UX: Allow groups page to be searchable.
This commit is contained in:
parent
0522aabaab
commit
05ea034490
|
@ -1,10 +1,18 @@
|
||||||
import { observes } from 'ember-addons/ember-computed-decorators';
|
import { observes } from 'ember-addons/ember-computed-decorators';
|
||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
export default Ember.Controller.extend({
|
export default Ember.Controller.extend({
|
||||||
application: Ember.inject.controller(),
|
application: Ember.inject.controller(),
|
||||||
queryParams: ["order", "asc"],
|
queryParams: ["order", "asc", "filter"],
|
||||||
order: null,
|
order: null,
|
||||||
asc: null,
|
asc: null,
|
||||||
|
filter: "",
|
||||||
|
filterInput: "",
|
||||||
|
|
||||||
|
@observes("filterInput")
|
||||||
|
_setFilter: debounce(function() {
|
||||||
|
this.set("filter", this.get("filterInput"));
|
||||||
|
}, 500),
|
||||||
|
|
||||||
@observes("model.canLoadMore")
|
@observes("model.canLoadMore")
|
||||||
_showFooter() {
|
_showFooter() {
|
||||||
|
|
|
@ -2,6 +2,7 @@ export default Discourse.Route.extend({
|
||||||
queryParams: {
|
queryParams: {
|
||||||
order: { refreshModel: true, replace: true },
|
order: { refreshModel: true, replace: true },
|
||||||
asc: { refreshModel: true, replace: true },
|
asc: { refreshModel: true, replace: true },
|
||||||
|
filter: { refreshModel: true }
|
||||||
},
|
},
|
||||||
|
|
||||||
refreshQueryWithoutTransition: true,
|
refreshQueryWithoutTransition: true,
|
||||||
|
|
|
@ -1,68 +1,74 @@
|
||||||
{{#d-section pageClass="groups"}}
|
{{#d-section pageClass="groups"}}
|
||||||
<h1>{{i18n "groups.index.title"}}</h1>
|
<h1>{{i18n "groups.index.title"}}</h1>
|
||||||
|
|
||||||
|
{{text-field value=filterInput
|
||||||
|
placeholderKey="groups.filter_name"
|
||||||
|
class="group-filter-name no-blur"}}
|
||||||
|
|
||||||
{{#if model}}
|
{{#if model}}
|
||||||
{{#load-more selector=".groups-table .groups-table-row" action="loadMore"}}
|
{{#conditional-loading-spinner condition=model.loading}}
|
||||||
<div class='container'>
|
{{#load-more selector=".groups-table .groups-table-row" action="loadMore"}}
|
||||||
<table class="groups-table">
|
<div class='container'>
|
||||||
<thead>
|
<table class="groups-table">
|
||||||
<th></th>
|
<thead>
|
||||||
{{directory-toggle field="user_count" labelKey="groups.user_count" order=order asc=asc}}
|
<th></th>
|
||||||
<th>{{i18n "groups.membership"}}</th>
|
{{directory-toggle field="user_count" labelKey="groups.user_count" order=order asc=asc}}
|
||||||
</thead>
|
<th>{{i18n "groups.membership"}}</th>
|
||||||
|
</thead>
|
||||||
|
|
||||||
<tbody>
|
<tbody>
|
||||||
{{#each model as |group|}}
|
{{#each model as |group|}}
|
||||||
<tr class="groups-table-row">
|
<tr class="groups-table-row">
|
||||||
<td class="groups-info">
|
<td class="groups-info">
|
||||||
{{#link-to "group.members" group.name}}
|
{{#link-to "group.members" group.name}}
|
||||||
{{#if group.flair_url}}
|
{{#if group.flair_url}}
|
||||||
<span class='group-avatar-flair'>
|
<span class='group-avatar-flair'>
|
||||||
{{avatar-flair
|
{{avatar-flair
|
||||||
flairURL=group.flair_url
|
flairURL=group.flair_url
|
||||||
flairBgColor=group.flair_bg_color
|
flairBgColor=group.flair_bg_color
|
||||||
flairColor=group.flair_color
|
flairColor=group.flair_color
|
||||||
groupName=group.name}}
|
groupName=group.name}}
|
||||||
|
</span>
|
||||||
|
{{/if}}
|
||||||
|
|
||||||
|
<span>
|
||||||
|
<span class='groups-info-name'>{{group.displayName}}</span>
|
||||||
|
|
||||||
|
{{#if group.full_name}}
|
||||||
|
<span class='groups-info-full-name'>{{group.full_name}}</span>
|
||||||
|
{{/if}}
|
||||||
|
|
||||||
|
{{#if group.title}}
|
||||||
|
<div>
|
||||||
|
<span class='groups-info-title'>{{group.title}}</span>
|
||||||
|
</div>
|
||||||
|
{{/if}}
|
||||||
</span>
|
</span>
|
||||||
{{/if}}
|
{{/link-to}}
|
||||||
|
</td>
|
||||||
|
|
||||||
<span>
|
<td class="groups-user-count">{{group.user_count}}</td>
|
||||||
<span class='groups-info-name'>{{group.displayName}}</span>
|
|
||||||
|
|
||||||
{{#if group.full_name}}
|
<td>
|
||||||
<span class='groups-info-full-name'>{{group.full_name}}</span>
|
{{#group-membership-button model=group
|
||||||
{{/if}}
|
showMembershipStatus=true
|
||||||
|
groupUserIds=groups.extras.group_user_ids
|
||||||
|
showLogin='showLogin'}}
|
||||||
|
|
||||||
{{#if group.title}}
|
{{d-button icon="ban"
|
||||||
<div>
|
label=(if group.automatic 'groups.automatic_group' 'groups.closed_group')
|
||||||
<span class='groups-info-title'>{{group.title}}</span>
|
disabled=true}}
|
||||||
</div>
|
{{/group-membership-button}}
|
||||||
{{/if}}
|
</td>
|
||||||
</span>
|
</tr>
|
||||||
{{/link-to}}
|
{{/each}}
|
||||||
</td>
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
{{/load-more}}
|
||||||
|
|
||||||
<td class="groups-user-count">{{group.user_count}}</td>
|
{{conditional-loading-spinner condition=model.loadingMore}}
|
||||||
|
{{/conditional-loading-spinner}}
|
||||||
<td>
|
|
||||||
{{#group-membership-button model=group
|
|
||||||
showMembershipStatus=true
|
|
||||||
groupUserIds=groups.extras.group_user_ids
|
|
||||||
showLogin='showLogin'}}
|
|
||||||
|
|
||||||
{{d-button icon="ban"
|
|
||||||
label=(if group.automatic 'groups.automatic_group' 'groups.closed_group')
|
|
||||||
disabled=true}}
|
|
||||||
{{/group-membership-button}}
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
{{/each}}
|
|
||||||
</tbody>
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
{{/load-more}}
|
|
||||||
|
|
||||||
{{conditional-loading-spinner condition=model.loadingMore}}
|
|
||||||
{{else}}
|
{{else}}
|
||||||
<p>{{i18n "groups.index.empty"}}</p>
|
<p>{{i18n "groups.index.empty"}}</p>
|
||||||
{{/if}}
|
{{/if}}
|
||||||
|
|
|
@ -1,9 +1,15 @@
|
||||||
.groups-page {
|
.groups-page {
|
||||||
h1 {
|
h1 {
|
||||||
margin: 20px 0;
|
margin-bottom: 20px;
|
||||||
|
display: inline-block;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.group-filter-name {
|
||||||
|
display: inline-block;
|
||||||
|
float: right;
|
||||||
|
}
|
||||||
|
|
||||||
.groups-table {
|
.groups-table {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
|
|
||||||
|
|
|
@ -24,6 +24,10 @@ class GroupsController < ApplicationController
|
||||||
dir = params[:asc] ? 'ASC' : 'DESC'
|
dir = params[:asc] ? 'ASC' : 'DESC'
|
||||||
groups = Group.visible_groups(current_user, order ? "#{order} #{dir}" : nil)
|
groups = Group.visible_groups(current_user, order ? "#{order} #{dir}" : nil)
|
||||||
|
|
||||||
|
if (filter = params[:filter]).present?
|
||||||
|
groups = Group.search_groups(filter, groups: groups)
|
||||||
|
end
|
||||||
|
|
||||||
unless guardian.is_staff?
|
unless guardian.is_staff?
|
||||||
# hide automatic groups from all non stuff to de-clutter page
|
# hide automatic groups from all non stuff to de-clutter page
|
||||||
groups = groups.where(automatic: false)
|
groups = groups.where(automatic: false)
|
||||||
|
|
|
@ -432,6 +432,7 @@ en:
|
||||||
join: "Join Group"
|
join: "Join Group"
|
||||||
leave: "Leave Group"
|
leave: "Leave Group"
|
||||||
request: "Request to Join Group"
|
request: "Request to Join Group"
|
||||||
|
filter_name: "filter by group name"
|
||||||
message: "Message"
|
message: "Message"
|
||||||
automatic_group: Automatic Group
|
automatic_group: Automatic Group
|
||||||
closed_group: Closed Group
|
closed_group: Closed Group
|
||||||
|
|
|
@ -18,6 +18,16 @@ describe GroupsController do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
context 'searchable' do
|
||||||
|
it 'should return the right response' do
|
||||||
|
other_group = Fabricate(:group, name: 'testing')
|
||||||
|
get "/groups.json", params: { filter: 'test' }
|
||||||
|
|
||||||
|
expect(response.status).to eq(200)
|
||||||
|
expect(JSON.parse(response.body)["groups"].first["id"]).to eq(other_group.id)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
context 'sortable' do
|
context 'sortable' do
|
||||||
let!(:other_group) { Fabricate(:group, name: "zzzzzz", users: [user]) }
|
let!(:other_group) { Fabricate(:group, name: "zzzzzz", users: [user]) }
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue