FEATURE: support for filter=bookmarked and filter=liked in topic list
This commit is contained in:
parent
da3da6feee
commit
ea87f5fd8a
|
@ -260,7 +260,7 @@ class ListController < ApplicationController
|
|||
min_posts: params[:min_posts],
|
||||
max_posts: params[:max_posts],
|
||||
status: params[:status],
|
||||
bookmarked: params[:bookmarked].present?,
|
||||
filter: params[:filter],
|
||||
state: params[:state],
|
||||
search: params[:search]
|
||||
}
|
||||
|
|
|
@ -80,6 +80,23 @@ class PostAction < ActiveRecord::Base
|
|||
user_actions
|
||||
end
|
||||
|
||||
def self.lookup_for(user, topics, post_action_type_id)
|
||||
return if topics.blank?
|
||||
|
||||
map = {}
|
||||
PostAction.where(user_id: user.id, post_action_type_id: post_action_type_id, deleted_at: nil)
|
||||
.references(:post)
|
||||
.includes(:post)
|
||||
.where('posts.topic_id in (?)', topics.map(&:id))
|
||||
.order('posts.topic_id, posts.post_number')
|
||||
.pluck('posts.topic_id, posts.post_number')
|
||||
.each do |topic_id, post_number|
|
||||
(map[topic_id] ||= []) << post_number
|
||||
end
|
||||
|
||||
map
|
||||
end
|
||||
|
||||
def self.active_flags_counts_for(collection)
|
||||
return {} if collection.blank?
|
||||
|
||||
|
|
|
@ -46,6 +46,20 @@ class TopicList
|
|||
# Attach some data for serialization to each topic
|
||||
@topic_lookup = TopicUser.lookup_for(@current_user, @topics) if @current_user.present?
|
||||
|
||||
post_action_type =
|
||||
if @current_user.present?
|
||||
if @opts[:filter].present?
|
||||
if @opts[:filter] == "bookmarked"
|
||||
PostActionType.types[:bookmark]
|
||||
elsif @opts[:filter] == "liked"
|
||||
PostActionType.types[:like]
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
# Data for bookmarks or likes
|
||||
post_action_lookup = PostAction.lookup_for(@current_user, @topics, post_action_type) if post_action_type
|
||||
|
||||
# Create a lookup for all the user ids we need
|
||||
user_ids = []
|
||||
@topics.each do |ft|
|
||||
|
@ -56,6 +70,11 @@ class TopicList
|
|||
|
||||
@topics.each do |ft|
|
||||
ft.user_data = @topic_lookup[ft.id] if @topic_lookup.present?
|
||||
|
||||
if ft.user_data && post_action_lookup && actions = post_action_lookup[ft.id]
|
||||
ft.user_data.post_action_data = {post_action_type => actions}
|
||||
end
|
||||
|
||||
ft.posters = ft.posters_summary(avatar_lookup: avatar_lookup)
|
||||
ft.participants = ft.participants_summary(avatar_lookup: avatar_lookup, user: @current_user)
|
||||
ft.topic_list = self
|
||||
|
|
|
@ -2,6 +2,9 @@ class TopicUser < ActiveRecord::Base
|
|||
belongs_to :user
|
||||
belongs_to :topic
|
||||
|
||||
# used for serialization
|
||||
attr_accessor :post_action_data
|
||||
|
||||
scope :tracking, lambda { |topic_id|
|
||||
where(topic_id: topic_id)
|
||||
.where("COALESCE(topic_users.notification_level, :regular) >= :tracking",
|
||||
|
|
|
@ -7,7 +7,8 @@ class TopicListItemSerializer < ListableTopicSerializer
|
|||
:last_poster_username,
|
||||
:category_id,
|
||||
:op_like_count,
|
||||
:pinned_globally
|
||||
:pinned_globally,
|
||||
:bookmarked_post_numbers
|
||||
|
||||
has_many :posters, serializer: TopicPosterSerializer, embed: :objects
|
||||
has_many :participants, serializer: TopicPosterSerializer, embed: :objects
|
||||
|
@ -28,6 +29,16 @@ class TopicListItemSerializer < ListableTopicSerializer
|
|||
object.participants_summary || []
|
||||
end
|
||||
|
||||
def include_bookmarked_post_numbers?
|
||||
object.user_data &&
|
||||
object.user_data.post_action_data &&
|
||||
object.user_data.post_action_data.key?(PostActionType.types[:bookmark])
|
||||
end
|
||||
|
||||
def bookmarked_post_numbers
|
||||
object.user_data.post_action_data[PostActionType.types[:bookmark]]
|
||||
end
|
||||
|
||||
def include_participants?
|
||||
object.private_message?
|
||||
end
|
||||
|
|
|
@ -26,7 +26,7 @@ class TopicQuery
|
|||
state
|
||||
search
|
||||
slow_platform
|
||||
bookmarked
|
||||
filter
|
||||
).map(&:to_sym)
|
||||
|
||||
# Maps `order` to a columns in `topics`
|
||||
|
@ -311,17 +311,25 @@ class TopicQuery
|
|||
end
|
||||
end
|
||||
|
||||
if options[:bookmarked] && @user
|
||||
if (filter=options[:filter]) && @user
|
||||
action =
|
||||
if filter == "bookmarked"
|
||||
PostActionType.types[:bookmark]
|
||||
elsif filter == "liked"
|
||||
PostActionType.types[:like]
|
||||
end
|
||||
if action
|
||||
result = result.where('topics.id IN (SELECT pp.topic_id
|
||||
FROM post_actions pa
|
||||
JOIN posts pp ON pp.id = pa.post_id
|
||||
WHERE pa.user_id = :user_id AND
|
||||
pa.post_action_type_id = :bookmarked AND
|
||||
pa.post_action_type_id = :action AND
|
||||
pa.deleted_at IS NULL
|
||||
)', user_id: @user.id,
|
||||
bookmarked: PostActionType.types[:bookmark]
|
||||
action: action
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
result = result.where('topics.deleted_at IS NULL') if require_deleted_clause
|
||||
result = result.where('topics.posts_count <= ?', options[:max_posts]) if options[:max_posts].present?
|
||||
|
|
|
@ -40,9 +40,28 @@ describe TopicQuery do
|
|||
|
||||
end
|
||||
|
||||
context 'bookmarks' do
|
||||
it "filters and returns bookmarks correctly" do
|
||||
post = Fabricate(:post)
|
||||
reply = Fabricate(:post, topic_id: post.topic_id)
|
||||
|
||||
post2 = Fabricate(:post)
|
||||
|
||||
PostAction.act(user, post, PostActionType.types[:bookmark])
|
||||
PostAction.act(user, reply, PostActionType.types[:bookmark])
|
||||
TopicUser.change(user, post.topic, notification_level: 1)
|
||||
TopicUser.change(user, post2.topic, notification_level: 1)
|
||||
|
||||
query = TopicQuery.new(user, filter: 'bookmarked').list_latest
|
||||
|
||||
query.topics.length.should == 1
|
||||
query.topics.first.user_data.post_action_data.should == {PostActionType.types[:bookmark] => [1,2]}
|
||||
end
|
||||
end
|
||||
|
||||
context 'deleted filter' do
|
||||
it "filters deleted topics correctly" do
|
||||
topic = Fabricate(:topic, deleted_at: 1.year.ago)
|
||||
_topic = Fabricate(:topic, deleted_at: 1.year.ago)
|
||||
|
||||
TopicQuery.new(admin, status: 'deleted').list_latest.topics.size.should == 1
|
||||
TopicQuery.new(moderator, status: 'deleted').list_latest.topics.size.should == 1
|
||||
|
|
Loading…
Reference in New Issue