JBoss Seam – autoryzacja na podstawie uprawnień
Opisałem już jak utworzyć encję dla uprawnień, jednak nie pokazałem, jak dokonywać autoryzacji na ich podstawie. Dzisiaj zamierzam omówić kilka przykładów zabezpieczania komponentów oraz elementów strony.
Najprostrzym sposobem zabezpieczania komponentu jest użycie adnotacji @Restrict z pakietu org.jboss.seam.annotations.security. Oznaczenie nią klasy komponentu będzie skutkowało udostępnieniem funkcjonalności jedynie uprawnionym użytkownikom.
@Restrict
@Name("accountManager")
public class AccountManagerBean
implements AccountManager {
public void renewPassword() {}
public void enable() {}
public void disable() {}
public void delete() {}
}
W tym wypadku, aby uruchomić poszczególne metody, użytkownik musi posiadać uprawnienia kolejno: accountManager:renewPassword, accountManager:enable, accountManager:disable, accountManager:delete, czyli ogólnie [NAZWA_KOMPONENTU]:[NAZWA_METODY] (uprawnienia przedstawione w formie target:action).
Jednak czasem przydaje się możliwość zabezpieczenia jedynie wybranych metod, nie zaś całego komponentu. Wówczas należy adnotację przypisać do wybranych metod:
@Name("accountManager")
public class AccountManagerBean
implements AccountManager {
@Restrict
public void renewPassword() {}
public void enable() {}
@Restrict("#{s:hasPermission('account','update')}")
public void disable() {}
@Restrict("#{s:hasPermission('account','delete')}")
public void delete() {}
}
Dodatkowy parametr w przypadku metod disable i delete pozwala uzależnić powodzenie autoryzacji od posiadania przez użytkownika uprawnień innych niż wynikające z nazw komponentu i metod.
Istnieje też inny sposób przeprowadzenia autoryzacji metod – utworzenie własnej adnotacji odwołującej się do konkretnej akcji:
@Target({METHOD, PARAMETER})
@Documented
@Retention(RUNTIME)
@Inherited
@PermissionCheck
public @interface RenewPassword {
Class<?> value() default void.class;
}
Tak zdefiniowana adnotacja oznacza uprawnienie do akcji renewPassword komponentu określonego w parametrze value. Jeżeli parametr pozostanie domyślny, uprawnienie odwołuje się do komponentu, w którym znajduje się definicja wskazanej metody:
@Name("accountManager")
public class AccountManagerBean
implements AccountManager {
@RenewPassword
public void renewPassword() {}
public void enable() {}
@Update(Account.class)
public void disable() {}
@Delete(Account.class)
public void delete() {}
}
Oprócz nowo utworzonej adnotacji, wykorzystałem też dwie spośród czterech zdefiniowanych w pakiecie org.jboss.seam.annotations.security dla encji (@Insert, @Read, @Update, @Delete). W przykładzie oznaczają one uprawnienia account:update i account:delete.
Pozostało mi jeszcze przedstawienie autoryzacji dla elementów strony. W celu posłużę się zabezpieczonym menu z jednego z wcześniejszych przykładów. Grupa narzędzi administratora będzie się wyświetlać dla każdego zalogowanego użytkownika, ale element Użytkownicy będzie widoczny tylko dla posiadaczy uprawnienia account:read:
<rich:panelMenuGroup
label="Narzędzia administratora"
rendered="#{identity.loggedIn}">
<rich:panelMenuItem
label="Użytkownicy"
rendered="#{s:hasPermission('account','read')}" />
<rich:panelMenuItem
label="Ustawienia"
rendered="#{s:hasRole('admin')}" />
</rich:panelMenuGroup
Jak widać, dla elementu Ustawienia pozostawiłem starą autoryzację na podstawie roli.
Sama autoryzacja okazuje się niezwykle prosta. Trochę więcej kłopotów może sprawić utworzenie interfejsu do zarządzania uprawnieniami poszczególnych ról. Ale o tym napiszę innym razem.



