Browse Source

refactor(core): add contidion change detection to permission directive

pull/2261/head
mehmet-erim 7 years ago
parent
commit
b12b607fc8
  1. 52
      npm/ng-packs/packages/core/src/lib/directives/permission.directive.ts
  2. 21
      npm/ng-packs/packages/core/src/lib/tests/permission.directive.spec.ts

52
npm/ng-packs/packages/core/src/lib/directives/permission.directive.ts

@ -8,17 +8,22 @@ import {
ViewContainerRef,
TemplateRef,
Optional,
SimpleChanges,
OnChanges,
} from '@angular/core';
import { Store } from '@ngxs/store';
import { ConfigState } from '../states';
import { takeUntilDestroy } from '../utils';
import { Subscription } from 'rxjs';
@Directive({
selector: '[abpPermission]',
})
export class PermissionDirective implements OnInit, OnDestroy {
export class PermissionDirective implements OnInit, OnDestroy, OnChanges {
@Input('abpPermission') condition: string;
subscription: Subscription;
constructor(
private elRef: ElementRef,
private renderer: Renderer2,
@ -27,26 +32,37 @@ export class PermissionDirective implements OnInit, OnDestroy {
private vcRef: ViewContainerRef,
) {}
private check() {
if (this.subscription) {
this.subscription.unsubscribe();
}
this.subscription = this.store
.select(ConfigState.getGrantedPolicy(this.condition))
.pipe(takeUntilDestroy(this))
.subscribe(isGranted => {
if (this.templateRef && isGranted) {
this.vcRef.clear();
this.vcRef.createEmbeddedView(this.templateRef);
} else if (this.templateRef && !isGranted) {
this.vcRef.clear();
} else if (!isGranted && !this.templateRef) {
this.renderer.removeChild((this.elRef.nativeElement as HTMLElement).parentElement, this.elRef.nativeElement);
}
});
}
ngOnInit() {
if (this.condition) {
this.store
.select(ConfigState.getGrantedPolicy(this.condition))
.pipe(takeUntilDestroy(this))
.subscribe(isGranted => {
if (this.templateRef && isGranted) {
this.vcRef.clear();
this.vcRef.createEmbeddedView(this.templateRef);
} else if (this.templateRef && !isGranted) {
this.vcRef.clear();
} else if (!isGranted && !this.templateRef) {
this.renderer.removeChild(
(this.elRef.nativeElement as HTMLElement).parentElement,
this.elRef.nativeElement,
);
}
});
if (this.templateRef && !this.condition) {
this.vcRef.createEmbeddedView(this.templateRef);
}
}
ngOnDestroy(): void {}
ngOnChanges({ condition }: SimpleChanges) {
if ((condition || { currentValue: null }).currentValue) {
this.check();
}
}
}

21
npm/ng-packs/packages/core/src/lib/tests/permission.directive.spec.ts

@ -46,7 +46,10 @@ describe('PermissionDirective', () => {
describe('structural', () => {
beforeEach(() => {
spectator = createDirective(`<div id="test-element" *abpPermission="'test'">Testing Permission Directive</div>`);
spectator = createDirective(
'<div id="test-element" *abpPermission="condition">Testing Permission Directive</div>',
{ hostProps: { condition: '' } },
);
directive = spectator.directive;
});
@ -55,7 +58,10 @@ describe('PermissionDirective', () => {
});
it('should remove the element from DOM', () => {
expect(spectator.query('#test-element')).toBeFalsy();
expect(spectator.query('#test-element')).toBeTruthy();
expect(spectator.directive.subscription).toBeUndefined();
spectator.setHostInput({ condition: 'test' });
expect(spectator.directive.subscription).toBeTruthy();
grantedPolicy$.next(true);
expect(spectator.query('#test-element')).toBeTruthy();
grantedPolicy$.next(false);
@ -64,5 +70,16 @@ describe('PermissionDirective', () => {
grantedPolicy$.next(true);
expect(spectator.queryAll('#test-element')).toHaveLength(1);
});
describe('#subscription', () => {
it('should call the unsubscribe', () => {
const spy = jest.fn(() => {});
spectator.setHostInput({ condition: 'test' });
spectator.directive.subscription.unsubscribe = spy;
spectator.setHostInput({ condition: 'test2' });
expect(spy).toHaveBeenCalled();
});
});
});
});

Loading…
Cancel
Save