Real Life Case – Dyrektywa do obsługi ról

Hej! Czas wrócić do aktywności z nowymi wpisami – będzie więcej krótkich artykułów z przypadkami, które uznałem za interesujące lub sprytne podczas pracy z angularowymi aplikacjami. Dzisiaj pokażę, jak radzę sobie z warunkowym wyświetlaniem elementów na podstawie ról użytkownika. Zaprezentuję rozwiązanie, którego prekursorem był kolega z teamu –  Tomasz Borowski z https://angular-in-space.pl, a które stosuję do dzisiaj z wielką przyjemnością.

*hasRoleDirective

Naszym celem jest napisanie dyrektywy strukturalnej, którą będziemy mogli używać w następujący sposób w templatce:

Przekazujemy w tablicy określone role – a dyrektywa weryfikuje czy profil zalogowanego użytkownika posiada jedną z nich. Brzmi prosto. A kod…jest jeszcze prostszy! Jestem przekonany, że wyświetlałeś/aś elementy warunkowo już wiele razy przy użyciu dyrektywy *ngIf, prawda? Więc po co wynajdywać koło od nowa? Rozszerzmy ją i dodajmy co trzeba.

Sprytnie wykorzystujemy dziedziczenie i nadpisujemy pola klasy – this.ngIf oraz this.ngIfElse. Wstrzykujemy również serwis, który będzie weryfikować czy użytkownik posiada zadaną rolę – może być typowy auth.service, gdzie również jest trzymany profil użytkownika, wraz z jego rolami. Pamiętaj, że nazwa selektora musi być zgodna z nazwami inputów  (appHasRole, apphasRoleElse). Wpis nie zawiera opisu działania dyrektyw strukturalnych – jeśli nie są Ci znane, zapraszam do dedykowanego artykułu:

Angular – dyrektywy strukturalne

To jest całe rozwiązanie – używaj go śmiało z opcją „else” i tablicą wielu ról, którymi może dysponować użytkownik aplikacji. A może masz tylko profil użytkownika i admina i nie potrzebujesz tablicy parameterów z rolami ? Eksperymentuj! W takiej sytuacji wystarczy bezparametrowa dyrektywa *hasAdminRole lub *isAdmin.

Istnieje również pewien gotchas,  np. jeśli renderujesz dynamiczne komponenty  za pomocą ComponentFactoryResolver, to nie będziesz w stanie nałożyć dyrektywy strukturalnej jednocześnie z templateRef # (Angular na to nie pozwala). Musisz poczekać, aż na pewno element w DOM będzie dostępny i zawołać tworzenie komponentów w hooku ngAfterViewInit.

NIE ZADZIAŁA:

DOBRZE, ZADZIAŁA ;):

DEMO:

https://stackblitz.com/edit/angular-apgykt?embed=1&file=src/app/has-role.directive.ts

 

A kolejny wpis, o wykrywaniu niezamkniętych subskrybcji w RxJS 😉 Stay tuned!

Dodaj komentarz

Twój adres email nie zostanie opublikowany. Pola, których wypełnienie jest wymagane, są oznaczone symbolem *