创建自定义的 Angular 指令 (3)

2022-05-16  本文已影响0人  品品下午茶

在一个典型的 Angular 企业应用中,用户会被分配若干角色,角色又被分配相应的功能权限。于是,用户就可以访问其角色对应的应用功能,也称基于角色的访问控制(Role-based Access Control)。

本文会介绍如何创建一个自定义的结构指令,该指令会验证用户的角色,显示或移除应用功能的视图模板。

创建指令文件

首先,通过 Angular CLI 命令,创建指令的源代码文件。

ng generate directive permission

命令输出结果:

CREATE src/app/permission.directive.spec.ts (240 bytes)
CREATE src/app/permission.directive.ts (149 bytes)
UPDATE src/app/app.module.ts (696 bytes)

角色属性

打开 src/app/permission.directive.ts 指令文件,添加下列属性:

  @Input() appPermission: string[];
  private currentRole = ‘admin’;

角色验证

permission 组件类的构造函数中,添加两个参数:

constructor(private tmplRef: TemplateRef<any>, private vc: ViewContainerRef) {}

ngOnInit 方法中,添加权限验证的逻辑:

  ngOnInit() {
    if (this.appPermission.indexOf(this.currentRole) === -1) {
      this.vc.clear();
    } else {
      this.vc.createEmbeddedView(this.tmplRef);
    }
  }

如果 currentRole 表示的角色,出现在角色列表中,ViewContainerRef 会把产生的视图模板添加到 DOM 中,否则,从 DOM 中移除该视图模板。

页面效果

normal角色展示效果

检查视图模板代码:

<div _ngcontent-kqs-c15=“”>
    <p _ngcontent-kqs-c15="">['admin', 'normal']</p>
</div>
<!—bindings={
  "ng-reflect-app-permission": "admin,normal”
}—>
<!—bindings={
  "ng-reflect-app-permission": “admin”
}—>
admin角色展示效果

检查视图模板代码:

<div _ngcontent-rry-c15=“”>
    <p _ngcontent-rry-c15="">['admin', 'normal']</p>
</div>
<!—bindings={
  "ng-reflect-app-permission": "admin,normal”
}—>
<div _ngcontent-rry-c15=“”>
    <p _ngcontent-rry-c15="">['admin']</p>
</div>
<!—bindings={
  "ng-reflect-app-permission": “admin”
}—>

源代码

src/app/permission.directive.ts

import { Directive, Input, TemplateRef, ViewContainerRef } from '@angular/core’;

@Directive({
  selector: '[appPermission]’
})
export class PermissionDirective {

  // The name of the input property must have
  // the same name as the selector of the directive
  @Input() appPermission: string[];
  private currentRole = ‘admin’;

  constructor(private tmplRef: TemplateRef<any>, private vc: ViewContainerRef) {
  }

  ngOnInit() {
    if (this.appPermission.indexOf(this.currentRole) === -1) {
      this.vc.clear();
    } else {
      this.vc.createEmbeddedView(this.tmplRef);
    }
  }

}

src/app/app.component.html

<p>
  <input type="text” appAlphabet>
</p>

<div *appPermission="['admin', 'normal’]”>
  <p>['admin', 'normal']</p>
</div>

<div *appPermission="['admin’]”>
  <p>['admin']</p>
</div>
上一篇下一篇

猜你喜欢

热点阅读