FEATURE: show pending/redeemed invite count in tabs

This commit is contained in:
Arpit Jalan 2015-08-25 00:33:25 +05:30
parent f40f733269
commit 99edcddafb
9 changed files with 60 additions and 8 deletions

View File

@ -7,6 +7,7 @@ export default Ember.Controller.extend({
model: null, model: null,
filter: null, filter: null,
totalInvites: null, totalInvites: null,
invitesCount: null,
canLoadMore: true, canLoadMore: true,
invitesLoading: false, invitesLoading: false,
@ -58,6 +59,22 @@ export default Ember.Controller.extend({
return this.get('totalInvites') > 9; return this.get('totalInvites') > 9;
}.property('totalInvites'), }.property('totalInvites'),
pendingLabel: function() {
if (this.get('invitesCount.total') > 50) {
return I18n.t('user.invited.pending_tab_with_count', {count: this.get('invitesCount.pending')});
} else {
return I18n.t('user.invited.pending_tab');
}
}.property('invitesCount'),
redeemedLabel: function() {
if (this.get('invitesCount.total') > 50) {
return I18n.t('user.invited.redeemed_tab_with_count', {count: this.get('invitesCount.redeemed')});
} else {
return I18n.t('user.invited.redeemed_tab');
}
}.property('invitesCount'),
actions: { actions: {
rescind(invite) { rescind(invite) {

View File

@ -43,6 +43,11 @@ Invite.reopenClass({
return Em.Object.create(result); return Em.Object.create(result);
}); });
},
findInvitedCount(user) {
if (!user) { return Em.RSVP.resolve(); }
return Discourse.ajax("/users/" + user.get('username_lower') + "/invited_count.json").then(result => Em.Object.create(result.counts));
} }
}); });

View File

@ -4,8 +4,12 @@ import showModal from "discourse/lib/show-modal";
export default Discourse.Route.extend({ export default Discourse.Route.extend({
model(params) { model(params) {
this.inviteFilter = params.filter; const self = this;
return Invite.findInvitedBy(this.modelFor("user"), params.filter); Invite.findInvitedCount(self.modelFor("user")).then(function (result) {
self.set('invitesCount', result);
});
self.inviteFilter = params.filter;
return Invite.findInvitedBy(self.modelFor("user"), params.filter);
}, },
afterModel(model) { afterModel(model) {
@ -20,7 +24,8 @@ export default Discourse.Route.extend({
user: this.controllerFor("user").get("model"), user: this.controllerFor("user").get("model"),
filter: this.inviteFilter, filter: this.inviteFilter,
searchTerm: "", searchTerm: "",
totalInvites: model.invites.length totalInvites: model.invites.length,
invitesCount: this.get('invitesCount')
}); });
}, },

View File

@ -1,5 +1,9 @@
{{#if routeParam}} {{#if routeParam}}
{{#link-to route routeParam}}{{i18n label}}{{/link-to}} {{#if i18nLabel}}
{{#link-to route routeParam}}{{i18nLabel}}{{/link-to}}
{{else}}
{{#link-to route routeParam}}{{i18n label}}{{/link-to}}
{{/if}}
{{else}} {{else}}
{{#if route}} {{#if route}}
{{#link-to route}}{{i18n label}}{{/link-to}} {{#link-to route}}{{i18n label}}{{/link-to}}

View File

@ -6,8 +6,8 @@
<div class='user-invite-controls'> <div class='user-invite-controls'>
<div class='span15'> <div class='span15'>
<ul class="nav nav-pills"> <ul class="nav nav-pills">
{{nav-item route='userInvited.show' routeParam='pending' label='user.invited.pending_tab'}} {{nav-item route='userInvited.show' routeParam='pending' i18nLabel=pendingLabel}}
{{nav-item route='userInvited.show' routeParam='redeemed' label='user.invited.redeemed_tab'}} {{nav-item route='userInvited.show' routeParam='redeemed' i18nLabel=redeemedLabel}}
</ul> </ul>
</div> </div>

View File

@ -181,6 +181,16 @@ class UsersController < ApplicationController
can_see_invite_details: guardian.can_see_invite_details?(inviter) can_see_invite_details: guardian.can_see_invite_details?(inviter)
end end
def invited_count
inviter = fetch_user_from_params
pending_count = Invite.find_pending_invites_count(inviter)
redeemed_count = Invite.find_redeemed_invites_count(inviter)
render json: {counts: { pending: pending_count, redeemed: redeemed_count,
total: (pending_count.to_i + redeemed_count.to_i) } }
end
def is_local_username def is_local_username
users = params[:usernames] users = params[:usernames]
users = [params[:username]] if users.blank? users = [params[:username]] if users.blank?

View File

@ -151,13 +151,13 @@ class Invite < ActiveRecord::Base
group_ids group_ids
end end
def self.find_all_invites_from(inviter, offset=0) def self.find_all_invites_from(inviter, offset=0, limit=SiteSetting.invites_per_page)
Invite.where(invited_by_id: inviter.id) Invite.where(invited_by_id: inviter.id)
.includes(:user => :user_stat) .includes(:user => :user_stat)
.order('CASE WHEN invites.user_id IS NOT NULL THEN 0 ELSE 1 END', .order('CASE WHEN invites.user_id IS NOT NULL THEN 0 ELSE 1 END',
'user_stats.time_read DESC', 'user_stats.time_read DESC',
'invites.redeemed_at DESC') 'invites.redeemed_at DESC')
.limit(SiteSetting.invites_per_page) .limit(limit)
.offset(offset) .offset(offset)
.references('user_stats') .references('user_stats')
end end
@ -170,6 +170,14 @@ class Invite < ActiveRecord::Base
find_all_invites_from(inviter, offset).where('invites.user_id IS NOT NULL').order('invites.redeemed_at DESC') find_all_invites_from(inviter, offset).where('invites.user_id IS NOT NULL').order('invites.redeemed_at DESC')
end end
def self.find_pending_invites_count(inviter)
find_all_invites_from(inviter, 0, nil).where('invites.user_id IS NULL').count
end
def self.find_redeemed_invites_count(inviter)
find_all_invites_from(inviter, 0, nil).where('invites.user_id IS NOT NULL').count
end
def self.filter_by(email_or_username) def self.filter_by(email_or_username)
if email_or_username if email_or_username
where( where(

View File

@ -609,9 +609,11 @@ en:
truncated: "Showing the first {{count}} invites." truncated: "Showing the first {{count}} invites."
redeemed: "Redeemed Invites" redeemed: "Redeemed Invites"
redeemed_tab: "Redeemed" redeemed_tab: "Redeemed"
redeemed_tab_with_count: "Redeemed ({{count}})"
redeemed_at: "Redeemed" redeemed_at: "Redeemed"
pending: "Pending Invites" pending: "Pending Invites"
pending_tab: "Pending" pending_tab: "Pending"
pending_tab_with_count: "Pending ({{count}})"
topics_entered: "Topics Viewed" topics_entered: "Topics Viewed"
posts_read_count: "Posts Read" posts_read_count: "Posts Read"
expired: "This invite has expired." expired: "This invite has expired."

View File

@ -275,6 +275,7 @@ Discourse::Application.routes.draw do
get "users/:username/staff-info" => "users#staff_info", constraints: {username: USERNAME_ROUTE_FORMAT} get "users/:username/staff-info" => "users#staff_info", constraints: {username: USERNAME_ROUTE_FORMAT}
get "users/:username/invited" => "users#invited", constraints: {username: USERNAME_ROUTE_FORMAT} get "users/:username/invited" => "users#invited", constraints: {username: USERNAME_ROUTE_FORMAT}
get "users/:username/invited_count" => "users#invited_count", constraints: {username: USERNAME_ROUTE_FORMAT}
get "users/:username/invited/:filter" => "users#invited", constraints: {username: USERNAME_ROUTE_FORMAT} get "users/:username/invited/:filter" => "users#invited", constraints: {username: USERNAME_ROUTE_FORMAT}
post "users/action/send_activation_email" => "users#send_activation_email" post "users/action/send_activation_email" => "users#send_activation_email"
get "users/:username/activity" => "users#show", constraints: {username: USERNAME_ROUTE_FORMAT} get "users/:username/activity" => "users#show", constraints: {username: USERNAME_ROUTE_FORMAT}