From 88dcdf776bf1ea0f4cc9a4245a123ffdc2a4abb0 Mon Sep 17 00:00:00 2001 From: Sam Saffron Date: Thu, 23 Jul 2020 10:30:08 +1000 Subject: [PATCH] FEATURE: add tracked filter to topic lists This adds a special filter to topic lists that will filter to tracked and watched categories. To use it you can visit: `https://sitename/?filter=tracked` `https://sitename/unread?filter=tracked` and so on Note, we do not include explicitly tracked and watched topics **outside** of the tracked categories and tags. We can consider a `filter=all_tracked` to cover this edge case. --- lib/topic_query.rb | 27 +++++++++++++++++++++++ spec/components/topic_query_spec.rb | 33 +++++++++++++++++++++++++++++ 2 files changed, 60 insertions(+) diff --git a/lib/topic_query.rb b/lib/topic_query.rb index f030c83aba..a838e79e17 100644 --- a/lib/topic_query.rb +++ b/lib/topic_query.rb @@ -824,6 +824,33 @@ class TopicQuery action: action ) end + + if filter == "tracked" + sql = +<<~SQL + topics.category_id IN ( + SELECT cu.category_id FROM category_users cu + WHERE cu.user_id = :user_id AND cu.notification_level >= :tracking + ) + SQL + + if SiteSetting.tagging_enabled + sql << <<~SQL + OR topics.id IN ( + SELECT tt.topic_id FROM topic_tags tt WHERE tt.tag_id IN ( + SELECT tu.tag_id + FROM tag_users tu + WHERE tu.user_id = :user_id AND tu.notification_level >= :tracking + ) + ) + SQL + end + + result = result.where( + sql, + user_id: @user.id, + tracking: NotificationLevels.all[:tracking] + ) + end end result = result.where('topics.deleted_at IS NULL') if require_deleted_clause diff --git a/spec/components/topic_query_spec.rb b/spec/components/topic_query_spec.rb index 6d97abfcb9..fdfd67dabb 100644 --- a/spec/components/topic_query_spec.rb +++ b/spec/components/topic_query_spec.rb @@ -118,6 +118,39 @@ describe TopicQuery do end end + context 'tracked' do + it "filters tracked topics correctly" do + SiteSetting.tagging_enabled = true + + tag = Fabricate(:tag) + Fabricate(:topic, tags: [tag]) + topic2 = Fabricate(:topic) + + query = TopicQuery.new(user, filter: 'tracked').list_latest + expect(query.topics.length).to eq(0) + + TagUser.create!( + tag_id: tag.id, + user_id: user.id, + notification_level: NotificationLevels.all[:watching] + ) + + cu = CategoryUser.create!( + category_id: topic2.category_id, + user_id: user.id, + notification_level: NotificationLevels.all[:regular] + ) + + query = TopicQuery.new(user, filter: 'tracked').list_latest + expect(query.topics.length).to eq(1) + + cu.update!(notification_level: NotificationLevels.all[:tracking]) + + query = TopicQuery.new(user, filter: 'tracked').list_latest + expect(query.topics.length).to eq(2) + end + end + context 'deleted filter' do it "filters deleted topics correctly" do _topic = Fabricate(:topic, deleted_at: 1.year.ago)