feat: 🎸 add role set-grants ability

This commit is contained in:
Randall Morey committed 2021-09-30 15:21:45 -04:00
1 parent 1646132db3
commit 3022ca5a53
6 files changed
+112 -49

No files matched your search

+15
View File
@@ -0,0 +1,15 @@
import ModelAbility from './model';
/**
* Provides abilities for roles.
*/
export default class RoleAbility extends ModelAbility {
// =permissions
/**
* @type {boolean}
*/
get canSetGrants() {
return this.hasAuthorizedAction('set-grants');
}
}
+1
View File
@@ -0,0 +1 @@
export { default } from 'api/abilities/role';
+1
View File
@@ -9,6 +9,7 @@ export default factory.extend({
'read',
'update',
'delete',
'set-grants',
],
// eslint-disable-next-line ember/avoid-leaking-state-in-ember-objects
grant_strings: () => [
@@ -0,0 +1,17 @@
import { module, test } from 'qunit';
import { setupTest } from 'ember-qunit';
module('Unit | Abilities | Account', function (hooks) {
setupTest(hooks);
test('it reflects when a given account may set grants based on authorized_actions', function (assert) {
assert.expect(2);
const service = this.owner.lookup('service:can');
const model = {
authorized_actions: ['set-grants'],
};
assert.ok(service.can('setGrants role', model));
model.authorized_actions = [];
assert.notOk(service.can('setGrants role', model));
});
});
@@ -1,39 +1,43 @@
<Rose::Form
@onSubmit={{fn this.createGrant @addGrant}}
@cancel={{@cancel}}
@disabled={{@model.isSaving}}
as |form|
>
<Rose::List::KeyValue as |list|>
{{! Add grant field (only one per form) }}
<list.item as |item|>
<form.input
@contextual={{true}}
@name='grant'
@type='text'
@value={{this.newGrantString}}
as |input|
>
<item.key>
<input.label>{{t 'resources.role.grant.actions.create'}}</input.label>
</item.key>
<item.cell>
<input.field title={{t 'form.grant.help'}} />
</item.cell>
<item.cell>
<Rose::Button
@submit={{true}}
@disabled={{this.cannotSave}}
@style='secondary'
title={{t 'actions.add'}}
>
{{t 'actions.add'}}
</Rose::Button>
</item.cell>
</form.input>
</list.item>
</Rose::List::KeyValue>
</Rose::Form>
{{#if (can 'setGrants role' @model)}}
<Rose::Form
@onSubmit={{fn this.createGrant @addGrant}}
@cancel={{@cancel}}
@disabled={{@model.isSaving}}
as |form|
>
<Rose::List::KeyValue as |list|>
{{! Add grant field (only one per form) }}
<list.item as |item|>
<form.input
@contextual={{true}}
@name='grant'
@type='text'
@value={{this.newGrantString}}
as |input|
>
<item.key>
<input.label>{{t
'resources.role.grant.actions.create'
}}</input.label>
</item.key>
<item.cell>
<input.field title={{t 'form.grant.help'}} />
</item.cell>
<item.cell>
<Rose::Button
@submit={{true}}
@disabled={{this.cannotSave}}
@style='secondary'
title={{t 'actions.add'}}
>
{{t 'actions.add'}}
</Rose::Button>
</item.cell>
</form.input>
</list.item>
</Rose::List::KeyValue>
</Rose::Form>
{{/if}}
<Rose::Form
@onSubmit={{fn @submit this.grantStrings}}
@@ -61,6 +65,7 @@
@name='grant'
@type='text'
@value={{grant.value}}
@disabled={{if (can 'setGrants role' @model) false true}}
@error={{@model.errors.grant_strings}}
as |input|
>
@@ -72,23 +77,27 @@
</item.cell>
</form.input>
<item.cell>
<Rose::Button
@style='secondary'
@iconOnly='flight-icons/svg/trash-16'
title={{t 'actions.remove'}}
{{on 'click' (fn @removeGrant grant.value)}}
>
{{t 'actions.remove'}}
</Rose::Button>
{{#if (can 'setGrants role' @model)}}
<Rose::Button
@style='secondary'
@iconOnly='flight-icons/svg/trash-16'
title={{t 'actions.remove'}}
{{on 'click' (fn @removeGrant grant.value)}}
>
{{t 'actions.remove'}}
</Rose::Button>
{{/if}}
</item.cell>
</list.item>
{{/each}}
</Rose::List::KeyValue>
<form.actions
@disabled={{if @model.cannotSave @model.cannotSave}}
@submitText={{t 'actions.save'}}
@cancelText={{t 'actions.cancel'}}
/>
{{#if (can 'setGrants role' @model)}}
<form.actions
@disabled={{if @model.cannotSave @model.cannotSave}}
@submitText={{t 'actions.save'}}
@cancelText={{t 'actions.cancel'}}
/>
{{/if}}
</Rose::Form>
@@ -63,6 +63,26 @@ module('Acceptance | roles | grants', function (hooks) {
assert.equal(findAll(`${grantsForm} [name="grant"]`).length, grantsCount);
});
test('cannot set grants without proper authorization', async function (assert) {
assert.expect(4);
const authorized_actions = instances.role.authorized_actions.filter(
(item) => item !== 'set-grants'
);
instances.role.update({ authorized_actions });
await visit(urls.grants);
assert.equal(
findAll('main form').length,
1,
'New grant form is not displayed.'
);
assert.notOk(
find('main form button:not([type="submit"])'),
'Grant delete button is not displayed.'
);
assert.notOk(find('.rose-form-actions'), 'Form actions are not displayed.');
assert.ok(find('main form input[disabled]'), 'Grant fields are disabled.');
});
test('update a grant', async function (assert) {
assert.expect(1);
this.server.post(