FEATURE: Make admin user list sortable.

https://meta.discourse.org/t/make-admin-users-list-sortable-suggestion/47649
This commit is contained in:
giorgia 2017-02-20 14:42:33 +01:00 committed by Guo Xiang Tan
parent d3f07122c4
commit 576982484d
4 changed files with 109 additions and 43 deletions

View File

@ -0,0 +1,33 @@
import { iconHTML } from 'discourse-common/helpers/fa-icon';
import { bufferedRender } from 'discourse-common/lib/buffered-render';
export default Ember.Component.extend(bufferedRender({
tagName: 'th',
classNames: ['sortable'],
rerenderTriggers: ['order', 'ascending'],
buildBuffer(buffer) {
const icon = this.get('icon');
if (icon) {
buffer.push(iconHTML(icon));
}
buffer.push(I18n.t(this.get('i18nKey')));
if (this.get('field') === this.get('order')) {
buffer.push(iconHTML(this.get('ascending') ? 'chevron-up' : 'chevron-down'));
}
},
click() {
const currentOrder = this.get('order');
const field = this.get('field');
if (currentOrder === field) {
this.set('ascending', this.get('ascending') ? null : true);
} else {
this.setProperties({ order: field, ascending: null });
}
}
}));

View File

@ -1,9 +1,14 @@
import debounce from 'discourse/lib/debounce';
import { i18n } from 'discourse/lib/computed';
import AdminUser from 'admin/models/admin-user';
import { observes } from 'ember-addons/ember-computed-decorators';
export default Ember.Controller.extend({
query: null,
queryParams: ['order', 'ascending'],
order: 'seen',
ascending: null,
showEmails: false,
refreshing: false,
listFilter: null,
@ -39,14 +44,15 @@ export default Ember.Controller.extend({
this._refreshUsers();
}, 250).observes('listFilter'),
@observes('order', 'ascending')
_refreshUsers: function() {
var self = this;
this.set('refreshing', true);
AdminUser.findAll(this.get('query'), { filter: this.get('listFilter'), show_emails: this.get('showEmails') }).then(function (result) {
self.set('model', result);
}).finally(function() {
self.set('refreshing', false);
AdminUser.findAll(this.get('query'), { filter: this.get('listFilter'), show_emails: this.get('showEmails'), order: this.get('order'), ascending: this.get('ascending') }).then( (result) => {
this.set('model', result);
}).finally( () => {
this.set('refreshing', false);
});
},

View File

@ -22,7 +22,7 @@
{{#conditional-loading-spinner condition=refreshing}}
{{#if model}}
<table class='table users-list'>
<tr>
<thead>
{{#if showApproval}}
<th>{{input type="checkbox" checked=selectAll}}</th>
{{/if}}
@ -30,54 +30,79 @@
<th>{{i18n 'username'}}</th>
<th>{{i18n 'email'}}</th>
<th>{{i18n 'admin.users.last_emailed'}}</th>
<th>{{i18n 'last_seen'}}</th>
<th>{{i18n 'admin.user.topics_entered'}}</th>
<th>{{i18n 'admin.user.posts_read_count'}}</th>
<th>{{i18n 'admin.user.time_read'}}</th>
<th>{{i18n 'created'}}</th>
{{admin-directory-toggle field="seen" i18nKey='last_seen' order=order ascending=ascending}}
{{admin-directory-toggle field="topics_viewed" i18nKey="admin.user.topics_entered" order=order ascending=ascending}}
{{admin-directory-toggle field="posts_read" i18nKey="admin.user.posts_read_count" order=order ascending=ascending}}
{{admin-directory-toggle field="read_time" i18nKey="admin.user.time_read" order=order ascending=ascending}}
{{admin-directory-toggle field="created" i18nKey="created" order=order ascending=ascending}}
{{#if showApproval}}
<th>{{i18n 'admin.users.approved'}}</th>
{{/if}}
<th>&nbsp;</th>
</tr>
{{#each model as |user|}}
<tr class="user {{user.selected}} {{unless user.active 'not-activated'}}">
{{#if showApproval}}
</thead>
<tbody>
{{#each model as |user|}}
<tr class="user {{user.selected}} {{unless user.active 'not-activated'}}">
{{#if showApproval}}
<td>
{{#if user.can_approve}}
{{input type="checkbox" checked=user.selected}}
{{/if}}
</td>
{{/if}}
<td><a href="{{unbound user.path}}" data-user-card="{{unbound user.username}}">{{avatar user imageSize="small"}}</a></td>
<td>{{#link-to 'adminUser' user}}{{unbound user.username}}{{/link-to}}</td>
<td class='email'>{{unbound user.email}}</td>
<td>{{{unbound user.last_emailed_age}}}</td>
<td>{{{unbound user.last_seen_age}}}</td>
<td>{{number user.topics_entered}}</td>
<td>{{number user.posts_read_count}}</td>
<td>{{{unbound user.time_read}}}</td>
<td>{{{unbound user.created_at_age}}}</td>
{{#if showApproval}}
<td>
{{#if user.approved}}
{{i18n 'yes_value'}}
{{else}}
{{i18n 'no_value'}}
{{/if}}
</td>
{{/if}}
<td>
{{#if user.admin}}<i class="fa fa-shield" title="{{i18n 'admin.title'}}"></i>{{/if}}
{{#if user.moderator}}<i class="fa fa-shield" title="{{i18n 'admin.moderator'}}"></i>{{/if}}
</td>
</tr>
{{/each}}
<td>
<a href="{{unbound user.path}}" data-user-card="{{unbound user.username}}">
{{avatar user imageSize="small"}}
</a>
</td>
<td>
{{#link-to 'adminUser' user}}{{unbound user.username}}{{/link-to}}
</td>
<td class='email'>
{{unbound user.email}}
</td>
<td>
{{{unbound user.last_emailed_age}}}
</td>
<td>
{{{unbound user.last_seen_age}}}
</td>
<td>
{{number user.topics_entered}}
</td>
<td>
{{number user.posts_read_count}}
</td>
<td>
{{{unbound user.time_read}}}
</td>
<td>
{{{unbound user.created_at_age}}}
</td>
{{#if showApproval}}
<td>
{{#if user.approved}}
{{i18n 'yes_value'}}
{{else}}
{{i18n 'no_value'}}
{{/if}}
</td>
{{/if}}
<td>
{{#if user.admin}}
{{fa-icon "shield" title="admin.title" }}
{{/if}}
{{#if user.moderator}}
{{fa-icon "shield" title="admin.moderator" }}
{{/if}}
</td>
</tr>
{{/each}}
</tbody>
</table>
{{else}}
<p>{{i18n 'search.no_results'}}</p>
{{/if}}

View File

@ -31,8 +31,10 @@ $mobile-breakpoint: 700px;
width: 100%;
tr {text-align: left;}
td, th {padding: 8px;}
th {border-top: 1px solid dark-light-diff($primary, $secondary, 90%, -60%);}
th {border-top: 1px solid dark-light-diff($primary, $secondary, 90%, -60%); text-align: left;}
td {border-bottom: 1px solid dark-light-diff($primary, $secondary, 90%, -60%); border-top: 1px solid dark-light-diff($primary, $secondary, 90%, -60%);}
th.sortable i.fa-chevron-down,
th.sortable i.fa-chevron-up {margin-left: 0.5em;}
tr:hover { background-color: darken($secondary, 2.5%); }
tr.selected { background-color: lighten($primary, 80%); }
.filters input { margin-bottom: 0; }