Replace dropdowns with autocomplete, for "find principals by perm"

This commit is contained in:
Lance Edgar 2023-10-18 17:35:14 -05:00
parent f86cc83996
commit 659f5a8fe1
3 changed files with 173 additions and 47 deletions

View file

@ -16,31 +16,52 @@
<div> <div>
${h.form(request.current_route_url(), method='GET', **{'@submit': 'formSubmitting = true'})} ${h.form(request.current_route_url(), method='GET', **{'@submit': 'formSubmitting = true'})}
<div style="margin-left: 10rem; max-width: 50%;">
${h.hidden('permission_group', **{':value': 'selectedGroup'})}
<b-field label="Permission Group" horizontal> <b-field label="Permission Group" horizontal>
<b-select name="permission_group" <b-autocomplete v-if="!selectedGroup"
v-model="selectedGroup" ref="permissionGroupAutocomplete"
@input="selectGroup"> v-model="permissionGroupTerm"
<option v-for="groupkey in sortedGroups" :data="permissionGroupChoices"
:key="groupkey" field="groupkey"
:value="groupkey"> :custom-formatter="filtr => filtr.label"
{{ permissionGroups[groupkey].label }} open-on-focus
</option> keep-first
</b-select> icon-pack="fas"
clearable
clear-on-select
@select="permissionGroupSelect">
</b-autocomplete>
<b-button v-if="selectedGroup"
@click="permissionGroupReset()">
{{ permissionGroups[selectedGroup].label }}
</b-button>
</b-field> </b-field>
${h.hidden('permission', **{':value': 'selectedPermission'})}
<b-field label="Permission" horizontal> <b-field label="Permission" horizontal>
<b-select name="permission" <b-autocomplete v-if="!selectedPermission"
v-model="selectedPermission"> ref="permissionAutocomplete"
<option v-for="perm in groupPermissions" v-model="permissionTerm"
:key="perm.permkey" :data="permissionChoices"
:value="perm.permkey"> field="permkey"
{{ perm.label }} :custom-formatter="filtr => filtr.label"
</option> open-on-focus
</b-select> keep-first
icon-pack="fas"
clearable
clear-on-select
@select="permissionSelect">
</b-autocomplete>
<b-button v-if="selectedPermission"
@click="permissionReset()">
{{ selectedPermissionLabel }}
</b-button>
</b-field> </b-field>
<div class="buttons"> <b-field horizontal>
<div class="buttons" style="margin-top: 1rem;">
<once-button tag="a" <once-button tag="a"
href="${request.current_route_url(_query=None)}" href="${request.current_route_url(_query=None)}"
text="Reset Form"> text="Reset Form">
@ -53,7 +74,9 @@
{{ formSubmitting ? "Working, please wait..." : "Find ${model_title_plural}" }} {{ formSubmitting ? "Working, please wait..." : "Find ${model_title_plural}" }}
</b-button> </b-button>
</div> </div>
</b-field>
</div>
${h.end_form()} ${h.end_form()}
% if principals is not None: % if principals is not None:
@ -91,24 +114,114 @@
data() { data() {
return { return {
groupPermissions: ${json.dumps(buefy_perms.get(selected_group, {}).get('permissions', []))|n}, groupPermissions: ${json.dumps(buefy_perms.get(selected_group, {}).get('permissions', []))|n},
permissionGroupTerm: '',
permissionTerm: '',
selectedGroup: ${json.dumps(selected_group)|n}, selectedGroup: ${json.dumps(selected_group)|n},
% if selected_permission:
selectedPermission: ${json.dumps(selected_permission)|n}, selectedPermission: ${json.dumps(selected_permission)|n},
% elif selected_group in buefy_perms: selectedPermissionLabel: ${json.dumps(selected_permission_label or '')|n},
selectedPermission: ${json.dumps(buefy_perms[selected_group]['permissions'][0]['permkey'])|n},
% else:
selectedPermission: null,
% endif
formSubmitting: false, formSubmitting: false,
} }
}, },
computed: {
permissionGroupChoices() {
// collect all groups
let choices = []
for (let groupkey of this.sortedGroups) {
choices.push(this.permissionGroups[groupkey])
}
// parse list of search terms
let terms = []
for (let term of this.permissionGroupTerm.toLowerCase().split(' ')) {
term = term.trim()
if (term) {
terms.push(term)
}
}
// filter groups by search terms
choices = choices.filter(option => {
let label = option.label.toLowerCase()
for (let term of terms) {
if (label.indexOf(term) < 0) {
return false
}
}
return true
})
return choices
},
permissionChoices() {
// collect all permissions for current group
let choices = this.groupPermissions
// parse list of search terms
let terms = []
for (let term of this.permissionTerm.toLowerCase().split(' ')) {
term = term.trim()
if (term) {
terms.push(term)
}
}
// filter permissions by search terms
choices = choices.filter(option => {
let label = option.label.toLowerCase()
for (let term of terms) {
if (label.indexOf(term) < 0) {
return false
}
}
return true
})
return choices
},
},
methods: { methods: {
selectGroup(groupkey) { permissionGroupSelect(option) {
this.selectedPermission = null
this.selectedPermissionLabel = null
if (option) {
this.selectedGroup = option.groupkey
this.groupPermissions = this.permissionGroups[option.groupkey].permissions
this.$nextTick(() => {
this.$refs.permissionAutocomplete.focus()
})
}
},
// re-populate Permission dropdown, auto-select first option permissionGroupReset() {
this.groupPermissions = this.permissionGroups[groupkey].permissions this.selectedGroup = null
this.selectedPermission = this.groupPermissions[0].permkey this.selectedPermission = null
this.selectedPermissionLabel = ''
this.$nextTick(() => {
this.$refs.permissionGroupAutocomplete.focus()
})
},
permissionSelect(option) {
if (option) {
this.selectedPermission = option.permkey
this.selectedPermissionLabel = option.label
}
},
permissionReset() {
this.selectedPermission = null
this.selectedPermissionLabel = null
this.permissionTerm = ''
this.$nextTick(() => {
this.$refs.permissionAutocomplete.focus()
})
}, },
} }
}) })

View file

@ -3,8 +3,8 @@
<%def name="context_menu_items()"> <%def name="context_menu_items()">
${parent.context_menu_items()} ${parent.context_menu_items()}
% if request.has_perm('{}.find_by_perm'.format(permission_prefix)): % if master.has_perm('find_by_perm'):
<li>${h.link_to("Find {} with Permission X".format(model_title_plural), url('{}.find_by_perm'.format(route_prefix)))}</li> <li>${h.link_to(f"Find {model_title_plural} by Permission", url(f'{route_prefix}.find_by_perm'))}</li>
% endif % endif
</%def> </%def>

View file

@ -77,7 +77,20 @@ class PrincipalMasterView(MasterView):
perms = self.get_buefy_perms_data(sorted_perms) perms = self.get_buefy_perms_data(sorted_perms)
context['buefy_perms'] = perms context['buefy_perms'] = perms
context['buefy_sorted_groups'] = list(perms) context['buefy_sorted_groups'] = list(perms)
context['selected_group'] = permission_group or 'common'
if permission_group and permission_group not in perms:
permission_group = None
if permission:
if permission_group:
group = dict([(p['permkey'], p) for p in perms[permission_group]['permissions']])
if permission in group:
context['selected_permission_label'] = group[permission]['label']
else:
permission = None
else:
permission = None
context['selected_group'] = permission_group
context['selected_permission'] = permission context['selected_permission'] = permission
return self.render_to_response('find_by_perm', context) return self.render_to_response('find_by_perm', context)