Merge pull request #1064 from theseyi/acl-refac

replaces page notifications for acl access requests with notification…
This commit is contained in:
Seyi Adebajo 2018-03-28 13:06:40 -07:00 committed by GitHub
commit a249e9ec52
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 53 additions and 96 deletions

View File

@ -1,9 +1,7 @@
import Component from '@ember/component'; import Component from '@ember/component';
import { get, set, getProperties, computed } from '@ember/object'; import { get, set } from '@ember/object';
import ComputedProperty from '@ember/object/computed';
import { TaskInstance, TaskProperty } from 'ember-concurrency'; import { TaskInstance, TaskProperty } from 'ember-concurrency';
import { action } from 'ember-decorators/object'; import { action } from 'ember-decorators/object';
import DatasetAclAccessContainer from 'wherehows-web/components/datasets/containers/dataset-acl-access';
import { IAccessControlAccessTypeOption } from 'wherehows-web/typings/api/datasets/aclaccess'; import { IAccessControlAccessTypeOption } from 'wherehows-web/typings/api/datasets/aclaccess';
import { getDefaultRequestAccessControlEntry } from 'wherehows-web/utils/datasets/acl-access'; import { getDefaultRequestAccessControlEntry } from 'wherehows-web/utils/datasets/acl-access';
@ -54,30 +52,6 @@ export default class DatasetAclAccess extends Component {
*/ */
removeAccessTask: TaskProperty<Promise<void>> & { perform: (a?: {} | undefined) => TaskInstance<Promise<void>> }; removeAccessTask: TaskProperty<Promise<void>> & { perform: (a?: {} | undefined) => TaskInstance<Promise<void>> };
/**
* External task reference to the last request for acl entry aliases `requestAccessAndCheckAccessTask`, if exists
* @type {ComputedProperty<TaskInstance<DatasetAclAccessContainer.requestAccessAndCheckAccessTask>>}
* @memberof DatasetAclAccess
*/
lastAccessRequestTask: ComputedProperty<TaskInstance<DatasetAclAccessContainer['requestAccessAndCheckAccessTask']>>;
/**
* Resolves to true if the last request for access results in an error and the logged in user,
* does not have access. Used to indicate that the request may have been denied
* @type {ComputedProperty<boolean>}
* @memberof DatasetAclAccess
*/
lastAccessRequestFailedOrDenied = computed('lastAccessRequestTask.isError', 'userHasAclAccess', function(
this: DatasetAclAccess
): boolean {
const { lastAccessRequestTask, userHasAclAccess } = getProperties(this, [
'lastAccessRequestTask',
'userHasAclAccess'
]);
const lastRequestErrored = lastAccessRequestTask && lastAccessRequestTask.isError;
return !!lastRequestErrored && !userHasAclAccess;
});
/** /**
* Action to reset the request form * Action to reset the request form
* @memberof DatasetAclAccess * @memberof DatasetAclAccess

View File

@ -1,5 +1,5 @@
import Component from '@ember/component'; import Component from '@ember/component';
import ComputedProperty, { equal, alias } from '@ember/object/computed'; import ComputedProperty, { equal } from '@ember/object/computed';
import { inject } from '@ember/service'; import { inject } from '@ember/service';
import { get, set, getProperties, computed } from '@ember/object'; import { get, set, getProperties, computed } from '@ember/object';
import { task, TaskInstance } from 'ember-concurrency'; import { task, TaskInstance } from 'ember-concurrency';
@ -19,6 +19,7 @@ import {
getDefaultRequestAccessControlEntry getDefaultRequestAccessControlEntry
} from 'wherehows-web/utils/datasets/acl-access'; } from 'wherehows-web/utils/datasets/acl-access';
import { hasEnumerableKeys } from 'wherehows-web/utils/object'; import { hasEnumerableKeys } from 'wherehows-web/utils/object';
import Notifications, { NotificationEvent } from 'wherehows-web/services/notifications';
export default class DatasetAclAccessContainer extends Component { export default class DatasetAclAccessContainer extends Component {
/** /**
@ -28,6 +29,13 @@ export default class DatasetAclAccessContainer extends Component {
*/ */
currentUser: ComputedProperty<CurrentUser> = inject(); currentUser: ComputedProperty<CurrentUser> = inject();
/**
* App notifications service
* @type {ComputedProperty<Notifications>}
* @memberof DatasetAclAccessContainer
*/
notifications: ComputedProperty<Notifications> = inject();
/** /**
* The currently logged in user * The currently logged in user
* @type {IUser} * @type {IUser}
@ -79,15 +87,6 @@ export default class DatasetAclAccessContainer extends Component {
*/ */
urn: string; urn: string;
/**
* Reference to the last requestAccessAndCheckAccessTask task
* @type {ComputedProperty<TaskInstance<DatasetAclAccessContainer.requestAccessAndCheckAccessTask>>}
* @memberof DatasetAclAccessContainer
*/
lastAccessRequestTask: ComputedProperty<
TaskInstance<DatasetAclAccessContainer['requestAccessAndCheckAccessTask']>
> = alias('requestAccessAndCheckAccessTask.last');
didInsertElement() { didInsertElement() {
get(this, 'getContainerDataTask').perform(); get(this, 'getContainerDataTask').perform();
} }
@ -108,6 +107,22 @@ export default class DatasetAclAccessContainer extends Component {
return hasEnumerableKeys(userAclRequest) && !!userAclRequest.businessJustification; return hasEnumerableKeys(userAclRequest) && !!userAclRequest.businessJustification;
}); });
/**
* Notifies user of changes to acl access
* @param {(string | Error)} param notification message string or error object
* @returns {void}
* @memberof DatasetAclAccessContainer
*/
notifyStatus(this: DatasetAclAccessContainer, param: string | Error) {
const { notify } = get(this, 'notifications');
if (typeof param === 'string') {
return notify(NotificationEvent.success, { content: param });
}
notify(NotificationEvent.error, { content: param.message });
}
/** /**
* Parent container task to get all data for the container component * Parent container task to get all data for the container component
* @memberof DatasetAclAccessContainer * @memberof DatasetAclAccessContainer
@ -173,9 +188,15 @@ export default class DatasetAclAccessContainer extends Component {
* @memberof DatasetAclAccessContainer * @memberof DatasetAclAccessContainer
*/ */
requestAccessAndCheckAccessTask = task(function*(this: DatasetAclAccessContainer): IterableIterator<any> { requestAccessAndCheckAccessTask = task(function*(this: DatasetAclAccessContainer): IterableIterator<any> {
try {
yield get(this, 'requestAccessTask').perform(); yield get(this, 'requestAccessTask').perform();
yield get(this, 'getDatasetAclsTask').perform(); yield get(this, 'getDatasetAclsTask').perform();
yield get(this, 'checkUserAccessTask').perform(); yield get(this, 'checkUserAccessTask').perform();
get(this, 'userHasAclAccess') && this.notifyStatus('Congrats, your request has been approved!');
} catch (e) {
this.notifyStatus(e);
}
}).drop(); }).drop();
/** /**
@ -187,9 +208,15 @@ export default class DatasetAclAccessContainer extends Component {
): IterableIterator< ): IterableIterator<
Promise<void> | TaskInstance<Array<IAccessControlEntry>> | TaskInstance<Promise<IAccessControlEntry[]>> Promise<void> | TaskInstance<Array<IAccessControlEntry>> | TaskInstance<Promise<IAccessControlEntry[]>>
> { > {
try {
yield removeAclAccess(get(this, 'urn')); yield removeAclAccess(get(this, 'urn'));
yield get(this, 'getDatasetAclsTask').perform(); yield get(this, 'getDatasetAclsTask').perform();
yield get(this, 'checkUserAccessTask').perform(); yield get(this, 'checkUserAccessTask').perform();
!get(this, 'userHasAclAccess') && this.notifyStatus('Your access has been removed');
} catch (e) {
this.notifyStatus(e);
}
}).drop(); }).drop();
/** /**

View File

@ -1,6 +1,4 @@
<header class="acl-permission__header"> <header class="acl-permission__header">
{{#unless lastAccessRequestTask}}
{{#if userHasAclAccess}} {{#if userHasAclAccess}}
<i class="fa fa-check-circle-o fa-lg acl-permission__success" title="You are in this dataset's ACL"></i> <i class="fa fa-check-circle-o fa-lg acl-permission__success" title="You are in this dataset's ACL"></i>
@ -19,47 +17,6 @@
</div> </div>
{{/if}} {{/if}}
{{/unless}}
{{#if lastAccessRequestFailedOrDenied}}
<i class="fa fa-ban fa-lg acl-permission__reject" title="You are not in this dataset's ACL"></i>
<div class="acl-permission__meta">
<strong class="acl-permission__reject acl-permission__meta__header">
Sorry, your request has been denied by the system or an error occured with your request.
</strong>
<p>If you feel this is in error, contact ask_acl@linkedin.</p>
</div>
{{/if}}
{{#if lastAccessRequestTask}}
{{#if userHasAclAccess}}
<i class="fa fa-check-circle-o fa-lg acl-permission__success" title="You are in this dataset's ACL"></i>
<div class="acl-permission__meta">
<strong class="acl-permission__success acl-permission__meta__header">
Congrats, your request has been approved.
</strong>
<p>You now have access to this dataset</p>
</div>
{{else}}
<i class="fa fa-ban fa-lg acl-permission__reject" title="You are not in this dataset's ACL"></i>
<div class="acl-permission__meta">
<strong class="acl-permission__reject acl-permission__meta__header">
Your access has been removed
</strong>
<p>You no longer have access to this dataset</p>
</div>
{{/if}}
{{/if}}
{{#if userHasAclAccess}} {{#if userHasAclAccess}}
<button <button

View File

@ -10,7 +10,6 @@
userAclRequest=userAclRequest userAclRequest=userAclRequest
userHasAclAccess=userHasAclAccess userHasAclAccess=userHasAclAccess
requestAccessAndCheckAccessTask=requestAccessAndCheckAccessTask requestAccessAndCheckAccessTask=requestAccessAndCheckAccessTask
lastAccessRequestTask=lastAccessRequestTask
removeAccessTask=removeAccessTask removeAccessTask=removeAccessTask
accessTypeDropDownOptions=accessTypeDropDownOptions accessTypeDropDownOptions=accessTypeDropDownOptions
expiresAtDidChange=(action "expiresAtDidChange") expiresAtDidChange=(action "expiresAtDidChange")