Files
zitadel/console/src/app/app.component.html
Max Peintner 42effd8702 feat(console): user grant filtering, org domain verification improvements, fix membership detail link (#916)
* user grant filter

* add filter input

* org domain spinner and reload

* user grant filter templates

* single selection filter for grants, same dl btn

* filter margin

* lint style, remove duplicate code

* project count as observable

* deferred reload on delete

* fix user grant formfield

* lint styles

* fix event propagation on pin, change selection

* propagate counter change

* admin warn, localstorage, i18n, sidenav impv

* overlays

* adapt toolbar elevationn, card

* color vars, i18n, admin section

* fix lint

* selection clear on filter

* ts lint

* Update console/src/assets/i18n/de.json

Co-authored-by: Fabi <38692350+fgerschwiler@users.noreply.github.com>

* Update console/src/assets/i18n/de.json

Co-authored-by: Fabi <38692350+fgerschwiler@users.noreply.github.com>

* Update console/src/assets/i18n/en.json

Co-authored-by: Fabi <38692350+fgerschwiler@users.noreply.github.com>

Co-authored-by: Fabi <38692350+fgerschwiler@users.noreply.github.com>
2020-11-13 09:59:11 +01:00

184 lines
10 KiB
HTML
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<ng-container *ngIf="(authService.user | async) || {} as user">
<ng-container *ngIf="((['iam.read$','iam.write$'] | hasRole)) as iamuser$">
<mat-toolbar class="root-header">
<button aria-label="Toggle sidenav" mat-icon-button (click)="drawer.toggle()">
<i class="icon las la-bars"></i>
</button>
<a *ngIf="(isHandset$ | async) == false" class="title" [routerLink]="['/']">
<img class="logo" alt="zitadel logo" *ngIf="componentCssClass == 'dark-theme'; else lighttheme"
src="../assets/images/zitadel-logo-light.svg" />
<ng-template #lighttheme>
<img alt="zitadel logo" class="logo" src="../assets/images/zitadel-logo-dark.svg" />
</ng-template>
</a>
<button (click)="loadOrgs()" *ngIf="profile?.id && org" mat-button [matMenuTriggerFor]="menu"
(menuOpened)="focusFilter()">{{org?.name ? org.name : 'NO NAME'}}
<mat-icon>
arrow_drop_down</mat-icon>
</button>
<mat-menu class="menu" #menu="matMenu">
<div class="spinner-w">
<mat-spinner diameter="20" *ngIf="orgLoading$ | async" color="accent">
</mat-spinner>
</div>
<mat-form-field class="filter-form" appearance="fill">
<input matInput [formControl]="filterControl" autocomplete="off" (click)="$event.stopPropagation()"
placeholder="{{'ORG.PAGES.FILTERPLACEHOLDER' | translate}}" #input>
</mat-form-field>
<div class="org-wrapper">
<button [ngClass]="{'active': temporg.id === org?.id}" [disabled]="!temporg.id"
*ngFor="let temporg of orgs$ | async" mat-menu-item (click)="setActiveOrg(temporg)">
{{temporg?.name ? temporg.name : 'NO NAME'}}
</button>
</div>
<button class="show-all" mat-menu-item
[routerLink]="[ '/org/overview' ]">{{'MENU.SHOWORGS' | translate}}</button>
<ng-template appHasRole [appHasRole]="['org.create','iam.write']">
<button mat-menu-item [routerLink]="[ '/org/create' ]">
<mat-icon class="avatar">add</mat-icon>
{{'MENU.NEWORG' | translate}}
</button>
</ng-template>
</mat-menu>
<span class="fill-space"></span>
<div (clickOutside)="closeAccountCard()" class="icon-container">
<app-avatar *ngIf="user && (user.displayName || (user.firstName && user.lastName))"
class="avatar dontcloseonclick" (click)="showAccount = !showAccount" [active]="showAccount"
[name]="user.displayName ? user.displayName : (user.firstName + ' '+ user.lastName)" [size]="38">
</app-avatar>
<app-accounts-card @accounts class="a_card mat-elevation-z5" *ngIf="showAccount"
(close)="showAccount = false" [profile]="profile" [iamuser]="iamuser$ | async">
</app-accounts-card>
</div>
</mat-toolbar>
<mat-drawer-container class="main-container">
<mat-drawer #drawer class="sidenav" [mode]="(isHandset$ | async) ? 'over' : 'side'"
[opened]="!(isHandset$ | async)">
<div class="side-column">
<div class="list">
<ng-container *ngIf="authenticationService.authenticationChanged | async">
<a @navitem class="nav-item" [routerLinkActive]="['active']"
[routerLinkActiveOptions]="{ exact: true }" [routerLink]="['/users/me']">
<i class="icon las la-user-circle"></i>
<span class="label">{{ 'MENU.PERSONAL_INFO' | translate }}</span>
</a>
</ng-container>
<ng-container *ngIf="iamuser$ | async">
<div @navitem class="divider">
<div class="line"></div>
<span>{{'MENU.ADMINSECTION' | translate}}</span>
<div class="hiddenline"></div>
</div>
<a @navitem class="nav-item" [routerLinkActive]="['active']" [routerLink]="[ '/iam']">
<i class="icon las la-gem"></i>
<span class="label">{{'MENU.IAM' | translate}}</span>
</a>
</ng-container>
<div *ngIf="org" [@navAnimation]="org">
<ng-template appHasRole [appHasRole]="['org.read']">
<a @navitem class="nav-item" [routerLinkActive]="['active']" [routerLink]="[ '/org']">
<i class="icon las la-archway"></i>
<span
class="label">{{org?.name ? org.name : 'MENU.ORGANIZATION' | translate}}</span>
</a>
</ng-template>
<ng-template appHasRole [appHasRole]="['project.read(:[0-9]*)?']">
<div @navitem class="divider">
<div class="line"></div>
<span>{{'MENU.PROJECTSSECTION' | translate}}</span>
<div class="hiddenline"></div>
</div>
<a @navitem class="nav-item" [routerLinkActive]="['active']"
[routerLink]="[ '/projects']">
<i class="icon las la-layer-group"></i>
<div class="c_label">
<span>{{org?.name ? org.name : 'MENU.ORGANIZATION' | translate}}
{{'MENU.PROJECT' | translate}} </span>
<span *ngIf="(mgmtService?.ownedProjectsCount | async)"
class="count">{{mgmtService?.ownedProjectsCount | async}}</span>
</div>
</a>
<a @navitem
*ngIf="mgmtService?.grantedProjectsCount && (mgmtService?.grantedProjectsCount | async)"
class="nav-item" [routerLinkActive]="['active']"
[routerLink]="[ '/granted-projects']">
<i class="icon las la-layer-group"></i>
<div class="c_label">
<span>{{ 'MENU.GRANTEDPROJECT' | translate }}</span>
<span class="count">{{mgmtService?.grantedProjectsCount | async}}</span>
</div>
</a>
</ng-template>
<ng-template appHasRole [appHasRole]="['user.read(:[0-9]*)?']">
<div @navitem class="divider">
<div class="line"></div>
<span class="label">
{{ 'MENU.USERSECTION' | translate }}</span>
<div class="hiddenline"></div>
</div>
<a @navitem class="nav-item" [routerLinkActive]="['active']"
[routerLink]="[ '/users/list/humans']" [routerLinkActiveOptions]="{ exact: true }">
<i class="icon las la-user-friends"></i>
<span class="label">{{ 'MENU.HUMANUSERS' | translate }}</span>
</a>
<a @navitem class="nav-item" [routerLinkActive]="['active']"
[routerLink]="[ '/users/list/machines']"
[routerLinkActiveOptions]="{ exact: true }">
<i class="icon las la-users-cog"></i>
<span class="label">{{ 'MENU.MACHINEUSERS' | translate }}</span>
</a>
</ng-template>
<ng-template appHasRole [appHasRole]="['user.grant.read(:[0-9]*)?']">
<div @navitem class="divider">
<div class="line"></div>
<span class="label">
{{ 'MENU.GRANTSECTION' | translate }}</span>
<div class="hiddenline"></div>
</div>
<a @navitem class="nav-item" [routerLinkActive]="['active']" [routerLink]="[ '/grants']"
[routerLinkActiveOptions]="{ exact: true }">
<i class="icon las la-shield-alt"></i>
<span class="label">{{ 'MENU.GRANTS' | translate }}</span>
</a>
</ng-template>
</div>
<span class="fill-space"></span>
</div>
<span class="fill-space"></span>
</div>
</mat-drawer>
<mat-drawer-content class="content">
<div class="router" [@routeAnimations]="prepareRoute(outlet)">
<router-outlet #outlet="outlet"></router-outlet>
</div>
</mat-drawer-content>
</mat-drawer-container>
<div @toolbar *ngIf="iamuser$ | async" class="admin-line" [ngClass]="{'expanded': !hideAdminWarn}"
matTooltip="IAM Administrator">
<button [matTooltip]="!hideAdminWarn ? 'Unpin': 'Pin'" (click)="toggleAdminHide()" mat-icon-button>
<mat-icon *ngIf="!hideAdminWarn" svgIcon="mdi_pin"></mat-icon>
<mat-icon *ngIf="hideAdminWarn" svgIcon="mdi_pin_outline"></mat-icon>
</button>
<span>{{'MENU.IAMADMIN' | translate}}</span>
</div>
</ng-container>
</ng-container>