Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
55 changes: 55 additions & 0 deletions app/models/topic.rb
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,61 @@ def participant_aliases(limit: 10)
participants
end

def participant_alias_stats(limit: 10)
stats = messages.group(:sender_id)
.select('sender_id, COUNT(*) as message_count, MAX(messages.created_at) AS last_at')
.order('message_count DESC')
.limit(50)
.index_by(&:sender_id)

first_sender = messages.order(:created_at).first&.sender
last_sender = messages.order(:created_at).last&.sender

missing_ids = [first_sender&.id, last_sender&.id].compact.uniq - stats.keys
if missing_ids.any?
extra_stats = messages.where(sender_id: missing_ids)
.group(:sender_id)
.select('sender_id, COUNT(*) as message_count, MAX(messages.created_at) AS last_at')
.index_by(&:sender_id)
stats.merge!(extra_stats)
end

sender_ids = stats.keys
senders_by_id = Alias.includes(person: :contributor_memberships).where(id: sender_ids).index_by(&:id)

entry_for = lambda do |alias_record|
return nil unless alias_record

stat = stats[alias_record.id]
{
alias: alias_record,
message_count: stat&.read_attribute(:message_count)&.to_i,
last_at: stat&.read_attribute(:last_at)
}
end

participants = []

participants << entry_for.call(first_sender) if first_sender

first_and_last = [first_sender&.id, last_sender&.id].compact.uniq
other_senders = sender_ids - first_and_last
remaining = [limit - first_and_last.length, 0].max
other_participants = other_senders
.map { |id| senders_by_id[id] }
.compact
.sort_by { |s| -stats[s.id].read_attribute(:message_count).to_i }
.take(remaining)

participants.concat(other_participants.map { |alias_record| entry_for.call(alias_record) }.compact)

if last_sender && last_sender.id != first_sender&.id
participants << entry_for.call(last_sender)
end

participants.compact
end

def has_contributor_activity?
@has_contributor_activity ||= begin
contributor_people = ContributorMembership.select(:person_id).distinct
Expand Down
26 changes: 17 additions & 9 deletions app/views/topics/_avatar_list.slim
Original file line number Diff line number Diff line change
@@ -1,15 +1,23 @@
.participants
.participants-avatars
- participants.each do |participant|
- alias_record = participant[:alias] || participant
- next unless alias_record
- message_count = participant[:message_count]
- last_at = participant[:last_at]
- tooltip_parts = []
- tooltip_parts << pluralize(message_count, "message") if message_count
- tooltip_parts << "last #{smart_time_display(last_at)}" if last_at
- role_label = alias_record.contributor_badge || "User"
- tooltip_parts << role_label
- badge_text = tooltip_parts.any? ? tooltip_parts.join(", ") : "#{alias_record.name} (#{role_label})"
- css_classes = ["participant-avatar"]
- css_classes << "is-core-team" if participant.core_team?
- css_classes << "is-committer" if !participant.core_team? && participant.committer?
- css_classes << "is-major-contributor" if !participant.core_team? && !participant.committer? && participant.major_contributor?
- css_classes << "is-significant-contributor" if !participant.core_team? && !participant.committer? && !participant.major_contributor? && participant.significant_contributor?
- css_classes << "is-past-contributor" if participant.past_contributor?
- role_label = participant.contributor_badge || "User"
- badge_text = "#{participant.name} (#{role_label})"
= link_to person_path(participant.email), class: "participant-avatar-link" do
= image_tag participant.display_gravatar_url(size: 32), class: css_classes.join(" "), alt: participant.name, title: badge_text
- css_classes << "is-core-team" if alias_record.core_team?
- css_classes << "is-committer" if !alias_record.core_team? && alias_record.committer?
- css_classes << "is-major-contributor" if !alias_record.core_team? && !alias_record.committer? && alias_record.major_contributor?
- css_classes << "is-significant-contributor" if !alias_record.core_team? && !alias_record.committer? && !alias_record.major_contributor? && alias_record.significant_contributor?
- css_classes << "is-past-contributor" if alias_record.past_contributor?
= link_to person_path(alias_record.email), class: "participant-avatar-link" do
= image_tag alias_record.display_gravatar_url(size: 32), class: css_classes.join(" "), alt: alias_record.name, title: badge_text
- if total_participants > participants.count
span.participants-count +#{total_participants - participants.count}
2 changes: 1 addition & 1 deletion app/views/topics/_topic_row_user.html.slim
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ tr id=dom_id(topic) class="topic-row topic-#{state[:status] || 'new'}" data-topi
.activity-replies = pluralize(replies_count, "reply")
.activity-time title=absolute_time_display(last_message.created_at) = smart_time_display(last_message.created_at)
td.topic-participants data-label="Participants"
- participants = topic.participant_aliases(limit: 5)
- participants = topic.participant_alias_stats(limit: 5)
- participant_count = topic.participant_count
= render partial: "avatar_list", locals: { participants: participants, total_participants: participant_count }
- if topic.has_contributor_activity?
Expand Down
2 changes: 1 addition & 1 deletion app/views/topics/_topics.html.slim
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
.activity-replies = pluralize(replies_count, "reply")
.activity-time title=absolute_time_display(last_message.created_at) = smart_time_display(last_message.created_at)
td.topic-participants data-label="Participants"
- participants = topic.participant_aliases(limit: 5)
- participants = topic.participant_alias_stats(limit: 5)
- participant_count = topic.participant_count
= render partial: "avatar_list", locals: { participants: participants, total_participants: participant_count }
- if topic.has_contributor_activity?
Expand Down