Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: kontrola dostepu
Forum PHP.pl > Forum > PHP > Pro > Archiwum Pro
evo
Witam,


Chial bym rozpoczac dyskusje na temat w jaki sposob projektuje sie system z kontrola dostepu.

Osobiscie jestem na etapie mojego pierwszego projektu ,ktory wymaga wiecej niz dwoch stanow (admin, user), wymaga on grup o roznym zakresie dostepu do systemu

Zabardzo nie wiem jak sie do tego zabrac.

Sam moj system/jadro laduje odpowiednie wtyczki,ktore sa odpowiedzialane za dostep do danych. Do tej pory kontrolowalem dostep na polacie wyboru akcji, bo kazdy plugin choc do innei zawartosci obsluguje te same akcje (add,remove,edit,show) wiec po wyborze wtyczki lecz przed wyborem akcji sprawdzalem czy uzytkownik ma prawo do tego, lecz teraz potrzebje wiekszej wolnosci tzn. niektorzy moga miec dostep do czegos do czego inni nie i na odwrot.

I zastanawiam sie czy nie przeniesc kontroli dostepu do samych akcji dostepu do danych, czy moze lepiej wymagac od wtyczki by opisala kto ma do jakich akcji dostep a sama kontrole zostawic w jadrze.




Wszelkie uwagi i pomysly sa mile widziane jak i wszelkiego rodzaju materialy, ktore wcale nie musza byc oparte na przykladach php, lecz duzym plusem by bylo gdyby opisywaly schemat kontroli dostepu w aplikacjach web. Jezyk Niemiecki,Angielski lub Polski.

Z gory dziekuje i pozdrawiam
evo
Ociu
Nauczyłem się używać i będę polecał: F-L-A-G-I.
Polecam ten art. bardzo fajnie napisany, mający dobre przykłady.
pozdrawiam
Ludvik
Osobiście stosuję autoryzację opartą na grupach i rolach. Każdy użytkownik może posiadać określone role i przynależeć do różnych grup.

Akcja wymaga posiadania wszystkich ról lub bycia w jednej z określonych grup.

Na przykład mamy administratora i newswritera. Admin należy tylko do grupy "admins", a newswriter może tylko pisać newsy, dlatego dostaje tylko role NewsWriter, NewsEditor etc... Akcja wpisywania wiadomości wymaga przynależności do grupy admins lub posiadania roli NewsWriter. Wszystko ładnie da się zapisać używając podstawowych funkcji tablicowych.

Wydaje mi się, że elastyczność i poziom bezpieczeństwa są wystarczające. Uprawnienia możesz sprawdzać tylko przed wykonaniem pierwszej akcji, kłania się wzorzec Intercepting Filter.

Role i grupy użytkowników trzymamy razem z ich danymi, a wymagania akcji w konfiguracji.

Nie będzie też problemu z blokowaniem dostępu dla określonych grup/ról...
Ociu
coś podobnego miałem na myśli.

  1. <?php
  2. define('banned', 0);
  3. define('member', 2);
  4. # etc.
  5.  
  6. class AuthorizeMember implements IAuthorize {
  7. public function __contruct( $flag ) {
  8. if($flag & banned) $this->set(banned);
  9. }
  10.  
  11. public function set( $f ) {
  12. $this->memberAuthorize = $f;
  13. }
  14.  
  15. public function get() {
  16. return $this->memberAuthorize;
  17. }
  18. }
  19. ?>


Dla akcji:
  1. <?php
  2. class AuthorizeAction implements IAuthorize {
  3. public function __construct($action ) {
  4. $this->action = $action;
  5. }
  6. public function set($f) {
  7. $htis->conn->executeUpdate('UPDATE actions SET authorize='.$f.' WHERE name='.$this->action.'');
  8. }
  9.  
  10. public function get() {
  11. $w = $this->conn->execute("SELECT authorize FROM actions WHERE name='".$this->action."'");
  12. return $w->next();
  13. }
  14.  
  15. public function check($m) {
  16. return ($this->get() == $m) ? true : false;
  17. }
  18. }
  19. ?>


Sprawdzić można bardzo prosto:
  1. <?php
  2. class delete extends action {
  3. public function __construct(AuthorizeAction $action) {
  4. if($action->check($this->memberAuthorize->get())){ throw new TException(get_class($this) .': False') }
  5. }
  6. }
  7. ?>


pozdrawiam
Ludvik
Co do twojego kodu:

Ja bym nie dopuścił akcji do manipulacji przy autoryzacji, przenosisz część odpowiedzialności na akcje i tworzysz kolejne miejsce, w którym możesz błąd popełnić.

Jeżeli użytkownik nie ma prawa do uruchomienia akcji, to nawet nie powinien zostać stworzony jej obiekt. Filtr nie może przepuścić tej akcji, łatwiej jest zmienić w żądaniu nazwę akcji na chociażby "NoAuthorizationAction", która powiadomi użytkownika o braku odpowiednich uprawnień.

Gdzie później łapiesz ten wyjątek i co z nim dalej robisz? Brak uprawnień jak dla mnie nie jest sytuacją wyjątkową, tylko sygnałem, że trzeba pójść inną ścieżką akcji.

A co się stanie jak będziesz miał 50 akcji i zajdzie potrzeba zmiany interfejsu autoryzacji? Domyślam się, że to jest mało prawdopodobne, ale akcje są uzależnione od konkretnej implementacji systemu uwierzytelniania. Rozumiem, że na twoje potrzeby to rozwiązanie spełnia w 100% swoje zadanie, dlatego to jest taka mała uwaga.
SongoQ
Mam troszeczke inne podejscie, wiekszosc uprawnien stosuje na poziomie bazy danych, bo tak jak pisal @Ludvik kazdy byla w akcji moze spowodowac dostep do akcji. Tam gdzie sie nie da lub projekt nie moze byc oparty na uprawnieniach baz danych uprawnienie jest sprawdzane zanim wywolywana jest akcja.
Ociu
Cytat(Ludvik @ 2005-12-04 12:58:21)
Ja bym nie dopuścił akcji do manipulacji przy autoryzacji, przenosisz część odpowiedzialności na akcje i tworzysz kolejne miejsce, w którym możesz błąd popełnić.

Jeżeli użytkownik nie ma prawa do uruchomienia akcji, to nawet nie powinien zostać stworzony jej obiekt. Filtr nie może przepuścić tej akcji, łatwiej jest zmienić w żądaniu nazwę akcji na chociażby "NoAuthorizationAction", która powiadomi użytkownika o braku odpowiednich uprawnień.

Gdzie później łapiesz ten wyjątek i co z nim dalej robisz? Brak uprawnień jak dla mnie nie jest sytuacją wyjątkową, tylko sygnałem, że trzeba pójść inną ścieżką akcji.

A co się stanie jak będziesz miał 50 akcji i zajdzie potrzeba zmiany interfejsu autoryzacji? Domyślam się, że to jest mało prawdopodobne, ale akcje są uzależnione od konkretnej implementacji systemu uwierzytelniania. Rozumiem, że na twoje potrzeby to rozwiązanie spełnia w 100% swoje zadanie, dlatego to jest taka mała uwaga.

To tylko przyład. Nie będę się rozpisywał, aby nie tworzyć zbędnej dyskusji.
pozdrawiam
halfik
ja takie rzeczy tez robie w oparciu o grupy i role.
grupom nadaje sie role/uprawnienia a usera przypisuje do grupy lub kilku grup.
jesli ktora z grup ma uprawnienia do podjecia jakiejs tam akcji uzytkownikowi sie na nia zezwala, nawet jesli w 1 grupie akacja jest zabroniana a w innej dozwolona. powiedzmy ze zezwolenia maja wyzszy priorytet.

w razie gdy userowi trzeba uprawnien nad grupe, mozna powolac specjalna grupe tylko dla niego i jej nadac odp role. albo do systemu wprowadzic jakiegos rodzaju wyjatki. znaczy sie ze niektorzy uzytkownicy procz uprawnien wynikajacych z grup moga posiadac specyficzne dla siebie tylko uprawnienia ktore beda nadrzedne nad uprawiena grupowe.
Ludvik
Ja bym wyróżnił zabranianie od braku uprawnień... Jeżeli mówisz, że jedna grupa nie posiada ról potrzebnych do wykonania akcji, a druga je posiada, to jest prawidłowe zachowanie. Natomiast kiedy jedna grupa zabrania wykonania akcji, a druga wycofuje to, to według mnie nie jest najlepsze wyjście... W zasadzie zabranianie dostępu powinno mieć wyższy priorytet niż role zezwalające. Raczej blokowanie dostępu powinno być używane tylko tymczasowo i do blokowania większej ilości grup/ról. Chcesz wyciąć jedną rolę to po prostu usuwasz ją, a jeżeli chcesz nie dopuścić użytkownika do całej strony, wtedy usuwanie wszystkich uprawnień może stać się uporczywe, jeżeli chcesz je przywrócić.

Przypisywanie ról do grup... hmmm... myślałem nad czymś takim, ale się wycofałem i obecnie sama przynależność do grupy jest dla mnie jakąś rolą. Grupy wprowadziłem, aby iść na skróty: Po co mam wpisywać adminowi role addNews, editNews, removeNews, addArticle etc., skoro mogę go przyłączyć do grupy admins i nie pisać już tych ról? Rozumiem, że w twoim przypadku grupa admins może mieć jedną rolę np. doAll, ale to się moim zdaniem mija z celem - nazwa grupy jest wystarczająca do identyfikacji uprawnień. Po to zbieramy uprawnienia w grupy, aby potem nie pracować na xxx rolach.

Halfik: Jak przechowujesz dane o uprawnieniach?

Pozdrowienia...
halfik
Cytat
Jeżeli mówisz, że jedna grupa nie posiada ról potrzebnych do wykonania akcji, a druga je posiada, to jest prawidłowe zachowanie. Natomiast kiedy jedna grupa zabrania wykonania akcji, a druga wycofuje to, to według mnie nie jest najlepsze wyjście... W zasadzie zabranianie dostępu powinno mieć wyższy priorytet niż role zezwalające. Raczej blokowanie dostępu powinno być używane tylko tymczasowo i do blokowania większej ilości grup/ról. Chcesz wyciąć jedną rolę to po prostu usuwasz ją, a jeżeli chcesz nie dopuścić użytkownika do całej strony, wtedy usuwanie wszystkich uprawnień może stać się uporczywe, jeżeli chcesz je przywrócić.

tak zgadza sie, blokowanie powinno miec wyzszy priorytet nad zezwolenia - tak jest wszedzie i nie ma co plynac pod prad, tak ma chociazby ip-tables i cala reszta zabawek na linkach. wiec ok - zezwolenia sa podrzedne wzgledem accessow.

ale jak sie zastanowic nie zawzsze konieczne jest wprowadzanie zabraniania czegos. wystarczy ze user nie ma uprawnien i po sprawie. chociaz pewnie zdarza sie systemy, w ktorych zabranianie wykonywania czynnosci moze sie przydac - chociaz nie mam pomyslu gdzie. bo gdybysmy chcieli z jakiegos powodu "ukarac" usera to mu usuwamy uprawnienia. hmmm...

w sumie mozna tak jak na ip-tables, jesli piszemy jakis system ktory wymaga powaznej kontroli tego co moga i co robia userzy - nie wiem gdzies w bankowosci or something - nie mam pomyslu. ale mniejsza o to. chodzi o to, jak sie konfiguruje frewalla zeby byl bezpieczny. pkt 1. blokujesz wszystko i wszystkim, a pozniej zezwalasz na grupom na rozne akcje jak juz userzy zaczna plakac ze czegos nie moga zrobic winksmiley.jpg jest troche roboty, ale to gwarancja dobrze skonfigurowanego firewalla - podobna strategie pewnie mozna gdzies wykozsytac w php - tylko gdzie ? tongue.gif i have no idea tongue.gif

Cytat
Przypisywanie ról do grup... hmmm... myślałem nad czymś takim, ale się wycofałem i obecnie sama przynależność do grupy jest dla mnie jakąś rolą. Grupy wprowadziłem, aby iść na skróty: Po co mam wpisywać adminowi role addNews, editNews, removeNews, addArticle etc., skoro mogę go przyłączyć do grupy admins i nie pisać już tych ról? Rozumiem, że w twoim przypadku grupa admins może mieć jedną rolę np. doAll, ale to się moim zdaniem mija z celem - nazwa grupy jest wystarczająca do identyfikacji uprawnień. Po to zbieramy uprawnienia w grupy, aby potem nie pracować na xxx rolach.


nie nadawalbym grupie adminow takiej roli. raczej preferowalbym role powiedzmy hmmm... podstawowe, a nie role totalnej wladzy i jak cos to nadaje adminom wszystkie role podstawowe.

a wprowadzenie grup jest konieczne jesli powaznie myslimy o zarzadzaniu uprawnieniami userow - grupy masz teraz na chyba all systemach operacyyjnych - i to nie jest przypadek. wyobraz sobie np 5000 userow i ze kazdego bys mial pilnowac czy ma takie uprawnienia jakie powinnien miec - no masakra. albo jak nagle sie okaze ze - tutaj zalozmy ze to jakis system w duze firmie - ze pracownicy wydzialu finansow potrzebuja uprawnien do czegos tam - i jest ich np. 50 - po cholere ich szukac i kazdemu z osoba - jest grupa finanse jeden klik i po sprawie, ale to wszyscy wiemy.

a co do traktowania samej grupy jako juz jakiejs roli hmm... mozna, ale czy nie lepiej czarne zostawic czarnym a biale bialym? lepsza wieksza czytelnosc. jak zrobisz z grupy juz jakies prawo, to jak pozniej ktos sie dorwie do kodu, moze sie z tym dziwnie poczuc nim sie polapie pracownik nalezacy do grupy "dzial finanse" moze wykonac operacje X bo sama przynaleznosc do tego dzialu juz daje mu odp uprawnienie. sa grupy i sa role i ja raczej wolalbym zeby ich nie mieszac.

Cytat
Halfik: Jak przechowujesz dane o uprawnieniach?

chodzi Ci o to jak to przechowuje na bazie? no kazdy user ma powiazanie z tabela grup - jest to powiazanie typu jeden->wielu - czyli 1 user moze nalezec do N grup. dalej masz table zdefiniowanych rol. grupy sa powiazane z rola dokladnie jeden->wielu. i to chyba tyle.
Ludvik
Cytat
chociaz pewnie zdarza sie systemy, w ktorych zabranianie wykonywania czynnosci moze sie przydac - chociaz nie mam pomyslu gdzie. bo gdybysmy chcieli z jakiegos powodu "ukarac" usera to mu usuwamy uprawnienia. hmmm...


Sytuacja jest taka: banowanie i odbanowywanie. Masz użytkownika, który ma jakiś niepowtarzalny zestaw ról, który jest trudno przywrócić. Wtedy wygodniej jest wprowadzić rolę banned niż usuwać całą listę roli. Jak będziesz chciał mu przywrócić uprawnienia to co zrobisz? Nie widzę innego logicznego rozwiązania.

Cytat
ale mniejsza o to. chodzi o to, jak sie konfiguruje frewalla zeby byl bezpieczny. pkt 1. blokujesz wszystko i wszystkim, a pozniej zezwalasz na grupom na rozne akcje jak juz userzy zaczna plakac ze czegos nie moga zrobic winksmiley.jpg jest troche roboty, ale to gwarancja dobrze skonfigurowanego firewalla - podobna strategie pewnie mozna gdzies wykozsytac w php - tylko gdzie ?


To jest po części prawdziwe przy każdym systemie bazującym na rolach. Wyjątkiem są akcje, które nie wymagają ani jednej roli i grupy.

Co do grup to nie zrozumieliśmy się chyba. Grupy są na pewno potrzebne, tylko pytanie w jakiej formie? Ja mówię, że grupy mogą istnieć jako niebezpośrednie połączenie kilku ról. To znaczy, że wciąż istnieje podział na grupy i role (żeby nie obniżać elastyczności), ale grupy nie posiadają ról. Chcemy aby ktoś mógł tylko dodawać newsy, wtedy dostaje rolę addNews. Dzięki temu nie usunie go, ani nie zmodyfikuje. Jeżeli chcemy mieć "news admina", wtedy włączamy go do grupy newsAdmins. U ciebie ta grupa by posiadała role addNews, editNews, removeNews etc... U mnie po samej nazwie grupy można identyfikować co użytkownik może a co nie.

Twoje rozwiązanie cechuje trochę większa elastyczność, ale musisz te dane gdzieś zapisać, a przy dużej ilości użytkowników, ról, grup, akcji może to być uciążliwe. Ja zwalam odpowiedzialność na projektanta, żeby przemyślał dokładnie podział odpowiedzialności. Wypadało by zastanowić się kiedy to się sprawdza, a kiedy nie. Dzisiaj chyba za późno dla mnie, jutro szkoła jeszcze...

Co do przechowywania danych - źle zadałem pytanie. Chodzi mi o pobieranie ról z grup i przenoszenie wszystkich odpowiedzialności pomiędzy żądaniami. Pewnie masz tablicę z rolami zapisaną w sesji i ciekawi mnie jak sobie radzisz z dużą ilością użytkowników posiadajacych dużą ilość ról.

Jak wygląda u ciebie sprawa nietypowych użytkowników - gościa i administratora?
NuLL
Cytat
Co do grup to nie zrozumieliśmy się chyba. Grupy są na pewno potrzebne, tylko pytanie w jakiej formie? Ja mówię, że grupy mogą istnieć jako niebezpośrednie połączenie kilku ról. To znaczy, że wciąż istnieje podział na grupy i role (żeby nie obniżać elastyczności), ale grupy nie posiadają ról. Chcemy aby ktoś mógł tylko dodawać newsy, wtedy dostaje rolę addNews. Dzięki temu nie usunie go, ani nie zmodyfikuje. Jeżeli chcemy mieć "news admina", wtedy włączamy go do grupy newsAdmins. U ciebie ta grupa by posiadała role addNews, editNews, removeNews etc... U mnie po samej nazwie grupy można identyfikować co użytkownik może a co nie.

A co jesli uzytkownik ma miec mozliwosc tylko edycji swoich newsow ?
Pozatym robi sie problem kiedy mamy np. forum i trzeba nadawac prawa moderacji ? Macie na to jakis pomysl poza pisaniem osobnego accessController-a ?
halfik
Cytat
Sytuacja jest taka: banowanie i odbanowywanie. Masz użytkownika, który ma jakiś niepowtarzalny zestaw ról, który jest trudno przywrócić. Wtedy wygodniej jest wprowadzić rolę banned niż usuwać całą listę roli. Jak będziesz chciał mu przywrócić uprawnienia to co zrobisz? Nie widzę innego logicznego rozwiązania.

tak jesli mowimy o systemach w ktorych uzyteczne jest tymczasowe blokowanie userow to bez sensu by bylo cos usuwac zeby to za jakis czas znowu dodawac/ustawiac.

Cytat
Co do grup to nie zrozumieliśmy się chyba. Grupy są na pewno potrzebne, tylko pytanie w jakiej formie? Ja mówię, że grupy mogą istnieć jako niebezpośrednie połączenie kilku ról. To znaczy, że wciąż istnieje podział na grupy i role (żeby nie obniżać elastyczności), ale grupy nie posiadają ról. Chcemy aby ktoś mógł tylko dodawać newsy, wtedy dostaje rolę addNews. Dzięki temu nie usunie go, ani nie zmodyfikuje. Jeżeli chcemy mieć "news admina", wtedy włączamy go do grupy newsAdmins. U ciebie ta grupa by posiadała role addNews, editNews, removeNews etc... U mnie po samej nazwie grupy można identyfikować co użytkownik może a co nie.

jesli dobrze zrozumialem chcesz miec grupy rol - zeby nie przypisywac userowi kazdej z nich osobo, oraz pojedyncze role, gdy user nie potrzebuje wiecej jak 1 roli - co sie moze zdarzyc.

bo widzisz mojde podejscie jest nieco inne. grupa jest dla mnie jakas tam podstawowa jednostka organizacyjna - pakuje userow w paczki. sam user dla mnie nie ma uprawnien. uprawnienia maja grupy do ktorych on nalezy. to gwarantuje spora przejrzystosc calosci.

wiec: ja chce miec grupy opisane przez role. zas Ty chce miec grupy rol. hmmm...
to prawie to samo. przy czym to podejscie do ktorego ja sie przykleilem jak zauwazyles jest bardziej elastyczne i daje ciut wieksze mozliwosci. jesli porobisz grupy opiszesz je rolami i do grup przydzielisz userow, to procz tego ze userzy maja to czego chcesz - jakies uprawnienia, to ulatwiasz sobie zarzadzanie userami.

zreszta nie bardzo mi sie podoba ze chcesz miec zarowno grupy rol jak i pojedyncze role. zalozmy ze bedziesz mial ciut tych userow w systemie. ze ich liczba bedzie rosla w czasie. i tak zalozmy co pare dni bedziesz zmuszony przydzielic np. 1-10 userom pojedyncze uprawnienie, za pare dni to samo i znowu. gdybys nawet mial grupe ktora jest opisana tylko przez pojedyncza role - po prostu dodajesz usera do grupy i sie dalej tym nie martwisz. niby to samo. ale... co jesli bedzie trzeba w jakis sposob zmienic ta role, usunac albo cos? bedziesz musial ja odebrac N userom kazdemu z osoba - ja tylko sciagne ja grupie. i jeszcze: a co jesli za jakis czas bedziesz musial dodac userom ktorzy moga dodac np. tego newsa role do np. usuwania i edycji newsow? bedziesz musial usunac im ta pojedyncza role i przypisac im grupe rol "newAdmin" - dobrze rozumuje? jesli tak to troszke to malo wygodne.

generalnie nie przekonuje mnie to Twoje rozwiazanie. nawet jesli nie potrzebujesz wiecej, to dlaczego sobie zamykac pewne drogi na przyszlosc? zostane przy swoim i bede sie upieral ze userzy do grup a grupy opisane przez role.

Cytat
Twoje rozwiązanie cechuje trochę większa elastyczność, ale musisz te dane gdzieś zapisać, a przy dużej ilości użytkowników, ról, grup, akcji może to być uciążliwe. Ja zwalam odpowiedzialność na projektanta, żeby przemyślał dokładnie podział odpowiedzialności. Wypadało by zastanowić się kiedy to się sprawdza, a kiedy nie. Dzisiaj chyba za późno dla mnie, jutro szkoła jeszcze...


to rozwiazanie sie sprawdza od dziesiecioleci - zauwaz ze wszyskie dystrybuje linuxow z niego korzysaja od zarania dziejow. nawet ms w koncu to docenil i w winach xp czy 2k juz masz podobne rozwiazania.

co do przechowywania danych - jesli user sie loguje do systemu - sciagam z bazy info o jego uprawnieniach i trzymam na sesji, zadne nowum. generalnie jak mamy obiekt np. new zakladam ze obiekt wie jakie trzeba miec role zeby wymusic na nim dane operacje. wiec sprawdzamy na bazie grupy usera i sciagamy role ktorymi te jego grupy sa opisane i ladujemy na sesje.

i nie rozumiem problemu z duza iloscia uzytkownikow. martwisz sie o obciazenie bazy? czy czego?

Cytat
Co do przechowywania danych - źle zadałem pytanie. Chodzi mi o pobieranie ról z grup i przenoszenie wszystkich odpowiedzialności pomiędzy żądaniami. Pewnie masz tablicę z rolami zapisaną w sesji i ciekawi mnie jak sobie radzisz z dużą ilością użytkowników posiadajacych dużą ilość ról.

hehe no wlasnie smile.gif
a jaki upatrujesz problem w duzej ilosci userow z duza iloscia praw?

Cytat
Jak wygląda u ciebie sprawa nietypowych użytkowników - gościa i administratora?

jesli idzie o goscia to nie nalezy do zadnych grup - zatem nie ma rol. ale... jesli do przegladania czegos co gosc powinien przegladac sa potrzebne juz role - to mozna zrobic grupe Goscie opisac je tymi podstawowymi rolami i jesli ktos wchodzi na www - bo zgaduje ze o tym rozmawiamy - automatycznie zostaje potraktowany jak czlonek grupy goscie, jesli sie zaloguje - zmieniaja sie jego grupy i role. w sumie to bedziemy mieli grupe ktora de facto nie ma zadnego usera hehe.

a jesli chodzi o admina. mozna porobc rozne rodzaje adminow. tych najwyzszych, pol-adminow, adminow jakis sekcji itd. - tworzysz grupy i nadajesz im all mozliwe role, czy np 75% moziwych rol - co Ci trzeba.

Cytat
A co jesli uzytkownik ma miec mozliwosc tylko edycji swoich newsow ?
Pozatym robi sie problem kiedy mamy np. forum i trzeba nadawac prawa moderacji ? Macie na to jakis pomysl poza pisaniem osobnego accessController-a ?


ja bym zrobil dla samych tylko newsow: grupe adminow - moga all, grupe pol adminow - moga all na swoich newsach - i pozniej przydziela usera do odp. grupy. a nadawnie praw do dodawnia newsow bez mozliwosic edycji troszke moja sie z celem. ale jesli ktos chce pewnym userom pozowlic dodawac i edytowac ale juz nie usuwac - robi sobie 3 grupy zwiazana z newsami i przypisuje jej te 2 role, a usera do grupy.

no forum tak samo jak wszystko inne. grupy i role. tylko ze takie forum z prawdziwego zdarzenia to mody ktore moga cos na jakiejs tam tylko czesci forum. hm... no ale im wiecej takich czesci forum tym wiecej rol i nic poza tym. czyli zrobi sie np. grupe adminow - nada jej all role zwiazane z forum i np. 5 roznych grup modow, ktorym sie nada np. full role ale tylko do 1 kawalka forum - kazdej grupie do innego. no i dalej przydzielamy userow do odp. grup. i mamy adminow, modow jak i modow ktorzy moga dzialac np. na 3/5 forum.
Ludvik
Cytat
A co jesli uzytkownik ma miec mozliwosc tylko edycji swoich newsow ?
Pozatym robi sie problem kiedy mamy np. forum i trzeba nadawac prawa moderacji ? Macie na to jakis pomysl poza pisaniem osobnego accessController-a ?


Słuszna uwaga. Można wprowadzić parametryzowane role/grupy. Role były by opisywane przez parametry, dzięki czemu można by było przekazać dodatkowe informacje.

Załóżmy, że mamy grupę moderatorów "mods" i 10 różnych for. Chcemy nadać konkretnemu użytkownikowi możliwość moderacji for 2, 5 i 9. Dopisujemy go do grupy mods, ale podajemy identyfikatory for. Można to formalnie zapisać jako mods(2,5,9).
Jak użytkownik ma majstrować tylko przy swoich newsach, to zapisujemy go do grupy newsEditors(only_own). Jeżeli ma mieć prawo do wszystkiego to możemy zapisać to jako rola(*). Problem od strony użytkownika można rozwiązać w ten sposób. Teraz co z akcjami? Myślę, że można przyznać akcjom dostęp do parametrów akcji. Wtedy możemy porównywać konkretne parametry akcji z parametrami grup/ról. Ja przynajmniej tak to widzę.

Gdzieś to rozwiązanie jest używane, wystarczy wstukać w googlarce "parametrized role based access control".

Halfik:
Co do twojego podejścia, to przynaję ci rację. Nie chce mi się za dużo pisać, bo w 99% popieram.

Jaki problem widzę w przechowywaniu dużej ilości danych? Przy każdym żądaniu trzeba je odczytać, przeparsować plik sesyjny, potem zapisać. Miejsce też zajmują te dane. Niby duża strona będzie potrzebowała mocy i miejsca, ale kto uruchamia większe projekty na słabych serwerach?

Nie są to duże koszta, ale jednak są. Chociaż dobrze rozplanowany system będzie wolny od tej wady...

Acha... Co do pojedynczych ról: Myślę, że takie rozwiązanie przydaje się jednak czasem. Są to skrajne przypadki, ale jak sam powiedziałeś "nawet jesli nie potrzebujesz wiecej, to dlaczego sobie zamykac pewne drogi na przyszlosc?". Jak nie będziesz potrzebował, to po prostu nie będziesz przypisywał pojedynczych ról. Ogólnie tworzenie grupy z jedną rolą dla jednego użytkownika moim zdaniem mija się z celem, przerost formy nad treścią.
halfik
hmmm a w jakis sposob chcesz parametryzowac te grupy?
no zalozmy ze mamy ta grupe modow i 10 forum o id 1-10. i teraz chodzi mi o baze - chcesz wprowadzic jakas tabele opisujaca role grup czy co tam?

obajanis mi prosze ta koncepcje ale nie w obrebie ze mamy forum, ale w obrebie calego jakiegos tam systemu.
Ludvik
Wygląda to tak:

Mamy akcję, która manipuluje danymi. Chcemy mieć kilka różnych zestawów danych, które będą istniały niezależnie od siebie. Musimy jakoś identyfikować te zestawy - intuicyjnie będziemy je oznaczać liczbami naturalnymi. W momencie wywołania akcji musi być znany identyfikator zestawu. Przed wywołaniem akcji musimy do naszego kontrolera (za kontroler przyjmiemy system autoryzacji) przekazać:
- Nazwę akcji
- Parametry z jakimi ją wywołujemy
- Specyfikację dostępu (czyli grupy, role i ich parametry)

Następnie musimy mieć dostęp do obiektu użytkownika, który będzie zawierał informację o rolach i grupach oraz ich parametrach. Teraz możemy wszystko porównać.

Przykład:
Użytkownik posiada rolę doAction, do której musimy przekazać parametry - domyślnie nie ma żadnego. Podajemy numer zestawu - powiedzmy, że 1. Akcję więc opisujemy następująco: doAction(1). Co z grupami? Podając parametry dla grupy możemy je jednakowo przekazać wszystkim rolom (jeżeli nasza hierarchia wygląda tak jak u Halfika).

Akcja wymaga roli doAction. Możemy wydzielić trzy metody postępowania z parametrami:
1. Parametry są opcjonalne (to raczej tylko dla wstecznej zgodności...).
2. Parametry są wymagane - jeżeli nie ma żadnego, to rola nie ma sensu.
3. Nie ma parametrów.

Teraz przechodzimy do meritum sprawy biggrin.gif Kontroler otrzymuje żądanie autoryzacji tego użytkownika dla tej akcji oraz podaje parametry z jakimi ma zostać wywołana akcja. Używamy zestawu pierwszego, więc interesującym nas parametrem będzie "id", którego wartość będzie równa 1. Konfiguracja akcji wymaga posiadania roli doAction oraz parametru. Jak zatem powiedzieć kontrolerowi o co nam chodzi? Musimy w jakiś sposób przekazać mu informację o tym, że musimy znaleźć na liście parametrów roli konkretny parametr akcji. Zapiszmy to tak:

Kod
Required: doAction($id)


Teraz cały proces autoryzacji będzie wyglądał następująco:
1. Szukamy akcji doAction.
2. Pobieramy parametr id z żądania (posiada wartość 1).
3. Porównujemy listę parametrów roli (która w tym przypadku jest jednoelementowa, a jej jedyny element ma wartość 1).

Jeżeli znajdziemy parametr na liście, to zezwalamy na wywołanie akcji. W przeciwnym wypadku zmieniamy ścieżkę wykonania programu.

Tak to mniej więcej wygląda.

Uwagi:
- Kolejność parametrów jest ignorowana, szukamy tylko wspólnych elementów.
- Parametr może być dowolną wartością skalarną.
- Jeżeli chcemy wprowadzić dostęp do wszystkich zestawów, możemy przypisać roli użytkownika jeden parametr "*".
- Podział odpowiedzialności akcji musi być odpowiedni, aby nie pomieszać parametrów. Lepiej pomyśleć chwilę nad konstrukcją akcji niż mieszać przy konstrukcji parametrów.
- Jeżeli wywołamy akcję z fikcyjnym zestawem np. 13, wtedy użytkownik nie otrzyma uprawnień i może zostać wyrzucony błąd autoryzacji. To jest nieprawda, gdyż użytkownik nie ma prawa mieć dostępu do czegoś, co nie istnieje. Wypada sprawdzić wcześniej czy faktycznie ten zestaw istnieje.

Zapis parametrów w bazie jest luźny - lekko zmieniamy formę, w której zapisywaliśmy role/grupy. Musimy tylko umieć skojarzyć identyfikator zestawu z parametrami ról.

Update:
Tak by wyglądał przykłądowy wpis do bazy:
Kod
user = login
roles = doAction(1,5,9);doOtherAction(3);doAnything(*)
groups = someGroup(1,3,7)

Jeżeli grupa by wyglądała tak:
Kod
name = someGroup
roles = roleOne;roleTwo

To użytkownik by posiadał ostatecznie role doAction(1,5,9), doOtherAction(3), doAnything(*), roleOne(1,3,7), roleTwo(1,3,7). To jest tylko przykładowy zapis.

Mam nadzieję, że jest w miarę jasno i nie zapomniałem o niczym.
halfik
no dobra, a skad kontroler ma wiedziec jakie sa mozliwe parametry dla danej akcji? wklepywac to na stale w kod to raczej srednio ciekawy pomysl. czyli trzeba pocisnac na baze i opisac role mozliwymi parametrami. tak to chcesz zrobic?

widze ze tak tongue.gif

ale w tym momencie dodawanie rol staje sie ciut bardziej klopotliwe. bo jak pisac taki system dla kogos kto nie jest koderem, a ma to tylko adminowac, to ebdzie trzeba mu jakos umozliwisc dodawanie parametrow do roli. czyli mamy ciut wiecej roboty. ale czy warto hmm...?

wydaje mi sie ze tak, ale musialbym cos takiego napisac zeby zobaczyc o ile wiecej roboty przy tym i czy wiecej czasu w to wlozonego da wieksze mozliwosci bez utraty elastycznosci.

jak juz to zaimplementujsz daj znac jak rozwiazanie sie sprawdza winksmiley.jpg
Ludvik
Nic nie jest na stałe zakodowane. Wpisy do bazy wymagają tylko lekkiej zmiany. Standardowo robimy tak:
Kod
Akcja:
name = actionName
neededGroups = groupOne, groupTwo

Zmieniamy na taki kod
Kod
neededGroups = groupOne($param1, const, 1);groupTwo


Kontroler wie, że $param1 określa wartość parametru o nazwie "param1" przekazywanego do akcji. "const" do stały łańcuch znakowy, do którego będziemy porównywać parametry ról użytkownika.

Skąd kontroler ma wiedzieć jakie są parametry akcji? To proste, u mnie silnik jest zaprojektowany podobnie do phienda2. Na początku router tworzy na podstawie żądania http obiekt kontekstu, w którym przechowujemy m.in. nazwę akcji oraz jej parametry. Następnie wywoływane są filtry zgodnie z wzorcem Intercepting Filter. To każdego filtru trafia obiekt kontekstu i to na nim są dokonywane zmiany. Z niego wiemy o nazwie akcji oraz jej parametrach. Jeżeli coś nam w filtrze nie pasuje, to modyfikujemy te dane. Wystarczy stworzyć authorizingFilter i wkomponować w niego kontroler dostępu. Jak będzie czas to wezmę się za to, w tej chwili szukam czasu, żeby tutaj coś napisać i odpocząć. Koniec semestru, męczą nauczyciele...

Jaki interfejs dostanie administrator strony (nie programista)? To też nie jest problem, trzeba tylko umieć odpowiednio złożyć wszystko do kupy. Przynajmniej ja nie widzę w tym problemu. Oczywiście jeżeli chcesz mieć dokładnie wszystko dostępne bez ingerencji bezpośredniej do kodu/bazy, to trochę roboty będzie. Ale jak chciałbyś zrobić to bez parametryzowania? Obsługa specjalnej grupy to jest ingerencja w kod kontrolera/akcji, a tego nie chcemy... Raz zakodowany elastyczny system sprawdzi się lepiej niż system z licznymi wyjątkami. Zauważ, że przy parametryzowaniu takie dziwne sytuacje to norma. Po tym co przeczytałem o twoim rozwiązaniu taki użytkownik byłby wyjątkiem. A im więcej wyjątków tym więcej kodu, więcej miejsc, w któreych możesz popełnić błąd, zwiększenie stopnia złożoności... Nie widzę żadnych korzyści.

Tak więc jak mówiłem... Znajdę trochę czasu to przedstawię jakąś wersję powiedzmy samego panelu do administracji uprawnieniami, jak mówiłeś to by cię najbardziej interesowało. Zasadę działania kontrolera opisałem post wcześniej, więc z implementacją nie powinno być problemu.
halfik
Cytat
Jak będzie czas to wezmę się za to, w tej chwili szukam czasu, żeby tutaj coś napisać i odpocząć. Koniec semestru, męczą nauczyciele...


hehe, to jak kiedys juz to napiszesz walnij na forum "odczucia" juz po. mysle ze w trakcie implementacji dojdziesz do jakis ciekawych wnioskow.

ta sesja idzie hehe. ale Cie pociesze - ja do lutego musze oddac prace dyplomowa winksmiley.jpg


Cytat
Jaki interfejs dostanie administrator strony (nie programista)? To też nie jest problem, trzeba tylko umieć odpowiednio złożyć wszystko do kupy. Przynajmniej ja nie widzę w tym problemu. Oczywiście jeżeli chcesz mieć dokładnie wszystko dostępne bez ingerencji bezpośredniej do kodu/bazy, to trochę roboty będzie.


nom bedzie troszke zabawy zeby to bylo user friendly ("milusie" dla usera tongue.gif). ale problemu tez nie widze.

Cytat
Ale jak chciałbyś zrobić to bez parametryzowania? Obsługa specjalnej grupy to jest ingerencja w kod kontrolera/akcji, a tego nie chcemy...

eeee a gdzie ja pisalem o jakiejs specjalnej grupie? grupy przeciez sa na bazie i admin z poziomu jakiegos tam panelu moze je sobie dodawac, usuwac, edycowac i ogolnie czarowac na nich.

Cytat
Raz zakodowany elastyczny system sprawdzi się lepiej niż system z licznymi wyjątkami. Zauważ, że przy parametryzowaniu takie dziwne sytuacje to norma. Po tym co przeczytałem o twoim rozwiązaniu taki użytkownik byłby wyjątkiem. A im więcej wyjątków tym więcej kodu, więcej miejsc, w któreych możesz popełnić błąd, zwiększenie stopnia złożoności... Nie widzę żadnych korzyści.

do czego sie odnosisz z tymi wyjatkami?

Cytat
Tak więc jak mówiłem... Znajdę trochę czasu to przedstawię jakąś wersję powiedzmy samego panelu do administracji uprawnieniami, jak mówiłeś to by cię najbardziej interesowało. Zasadę działania kontrolera opisałem post wcześniej, więc z implementacją nie powinno być problemu.

mi nie chodzi o wersje czegokolwiek. ciekawi mnie na jakie problemy sie natkniesz podczas implementacji, ich rozwiazania i ogolnie wnioski koncowe. pewnie kiedys bede jeszcze potrzebowal napisac cos podobnego, a wiedzy nigdy za duzo.
Ludvik
Nie chodzi o to, że grupy są specjalne, ale trzeba je traktować specjalnie. Bo jak miałbyś zamiar zasygnalizować, że użytkownik jest właśnie autorem newsa? Sam się zastanawiam jak to zrobić u siebie, żeby nie trzeba było mieszać w kodzie. U mnie akcje nie mają dostępu do kontrolera dostępu i tutaj pojawia się problem - jak sprawdzić te sytuacje wyjątkowe? Ostatecznie można sprawdzić prostym wyrażeniem warunkowym już w akcji, ale nie podoba mi się to. Moje rozwiązanie polegało by na wprowadzeniu małych obiektów przypisywanych konkretnym akcjom, w których moglibyśmy sprawdzać rzeczy zależne od konkretnych akcji. Użytkownik wciąż by nie miał bezpośredniego dostępu do samej akcji. Jak wy ten problem widzicie?
Ace
małe obiekciki - najprosciej by bylo potraktowac je jako grupy...

masz odczyt na grupe news i mozliwosc tworzenia
kazdy nowo utworzony news tworzy tez grupe news_ID i dziedziczy on uprawnienia z news + masz dostep do usuniencia, edycji.

Jak chcesz komus jeszcze dac dostep do obiektu to przypisujesz go do tej grupy news_ID

Czytam sobei co jakis czas wasze przemyslenia, i sadze ze tez powinienem zabrac sie za projekt wlasnego systemu uprawnien, ale napewno bedzie sie opieral na grupach/rolach. Tworzymy grupe, dodajemy do niej role, czyli grupa ma jakies mozliwosci i wrzucamy usera w grupe. Uprawnienia sie sumuja z wszystkich grup.

Zastanawia mnie wydajnosc, gdyz chce poprac sobie liste ostatnich 30 newsow, (ostatnie newsy nie tylko te do ktorych ma mdostep) i chce zeby przy moich newsach byla ikonka edycja, a przy pozostalych nie. Jak to rozwiazuje? Zapytanie do bazy o 30 ostatnich newsow, a pozniej w petli sprawdzam jeszcze uprawnienia do pojedycnzego obiektu, czy moze juz podczas pobierania obiektu zapytanie jest skonstruowane w taki sposob zeby pobieral moje uprawnienia do tego obiektu?

Pozdrawiam.
Ludvik
Rzecz w tym, aby nie tworzyć niepotrzebnych grup, bo potem nie opanujesz tego. Zobaczymy jak sprawdzi się mój pomysł. Jako że w szkole dużo się dzieje, szukam czasu, żeby coś z kompem zrobić, to na pisanie prawie nie zostaje nic... Ale postaram się.

Ace: Co do twojego problemu. To jest takie trudne ani wolne.

Zgodnie z moim pomysłem wyglądało by to tak: Najpierw standardowo musimy mieć dostęp do ról i parametrów. Potem obiekt pomocniczy zajął by się szukaniem uprawnień związanych z edycją newsów, czyli po prostu roli editNews. Do wywołania akcji dodaje wszystkie parametry tej roli. Powiedzmy, że mamy trzy parametry: OWN, 3, 5. Pierwszy to stała oznaczająca możliwość edycji swoich newsów, a dwie kolejne to po prostu identyfikatory pozostałych zestawów, w których znajdują się newsy objęte możliwością edycji. Wywołujesz akcję i wykonujesz szybkie sprawdzenie dla każdego newsa po kolei:

1. Czy id użytkownika jest takie samo jak autora? Tak - dodajesz możliwość edycji. Nie - następny punkt...
2. Czy id zestawu newsa znajduje się pośród parametrów roli editNews (przekazaliśmy je jako parametr do akcji)? Tak - dodajesz możliwość edycji. Nie - nie ma możliwości zmian.

Zauważ, że nie wykonujesz ani jednego dodatkowego zapytania, a sprawdzanie jest bardzo szybkie.
Ociu
Myślę, że można zrobić tak:
Groups
Kod
| id |  name |         read         |        write        | delete |
| 1  | maker | news, articles, etc. | news, articles etc. |  null  |


Gdzie w write wchodzi także edytowanie.

Members
Kod
| id | Group_id | Username |
|  1 |    1     |   ociu   |


  1. <?php
  2. final class GroupAuthorize {
  3. public $group = array();
  4.  
  5. public function __construct( DataBase $db ) {
  6. $w = $db->execute('SELECT * FROM Groups');
  7. while($r = $w->next() {
  8. $this->group[$r['name']]['read'] = ($r['read'] == null) ? false : $r['read'];
  9. $this->group[$r['name']]['write'] = ($r['write'] == null) ? false : $r['write'];
  10. $this->group[$r['name']]['delete'] = ($r['delete'] == null) ? false : $r['delete'];
  11. } 
  12. }
  13. }
  14. ?>


Co wy na to ?
pozdrawiam
Ludvik
A jak ktoś zechce dodać możliwośc przenoszenia? Można dużo rzeczy wymyślić... Ja bym nie wiązał się za bardzo ze strukturą bazy danych, chyba że masz system, który nie będzie wymagał późniejszych zmian. Tak jest z systemem plików, gdzie nie trzeba się męczyć, aby dokładnie opisać uprawnienia.
halfik
ta ta tabela z rolami jest to chrzanu.
wlasnie o to chodzi ze wszsytko ma byc elastyczne. wchodzi admin, dodaje nowa role i to ma dzialac. wywala role i ma dzialac. itd.
ebe
U mnie jest tak 3 akcje podstawowe, add, edit, delete. Każda akcja na obiekcie w danej (podanej w url) gałęzi drzewa (np. drzewo content lub members)

Mamy 3 akcje więc uprawnienia wyglądają tak
Kod
| id | obj_id |  node_id | type     |
| 1  | 304     | 1302      |    edit  |


Gdzie obj_id może być memberem, może być members_group, może być każdym dowolnym obiektem, bo umnie wszystko jest wirtualnie stworzonym obiektem na podstaiwe wirtualnej klasy (jak w ez<-love it) oczywiście type może być obcym kluczem do types jakiejś tabeli w db zawierającej różne akcje, node_id to prawo do danego węzła (i jego pod węzłów!) dziedziczene praw jest w logice. Prawa dziedziczone są nie tylko przez węzły ale też przez grupy użytkowników

W przyszłości

- zastosowanie NOT czyli zabronienie to pozwoli na wyłączenie praw do podwęzłów danym podgrupom
- mam specjalne akcje create_class, delete_class, add_role itp. chcę to ujednolicić i sprawić by nawet klasy były obiektami (!) podobnie z rolami czyli zostały by mi 3 akcje w cmsie add, edit, delete biggrin.gif, klasy trzymałbym w kolejnym innym drzewie a role w specjalnym folderze danej grupy użytkowników, ale to wymaga zastanowienia i wymyślenia jak to ma działać i jak zrobić by działało szybko
Ludvik
Hmmm... trochę niejasny ten opis dla mnie, przynajmniej nie rozumiem dlaczego ograniczasz się tylko do trzech akcji(?). A jak by wyglądało u ciebie rozwiązanie dwóch podstawowych problemów - edycji tylko własnych newsów oraz moderacji forum?

Poza tym nie wszystko na tym świecie da się opisać w trzech słowach - dodaj, usuń, edytuj, a tak odbieram właśnie twoje rozwiązanie. Co z wyświetlaniem? Co zrobisz w sytuacji, kiedy użytkownik ma mieć dostęp tylko do części obiektu? Możliwośc edycji ma, ale nie do końca. Właśnie w takich dziwnych sytuacjach role wydają się być przyjaźniejszym narzędziem.

Jeżeli Cię źle zrozumiałem, to wyjaśnij to trochę dokładniej z przykładami.
splatch
uprawnienia ograniczone do read, write, delete to pomyłka. Pomyłka dlatego, że chcemy dać możliwość zmieniania autorowi treści którą wprowadził do systemu, ale chcemy zablokować możliwość zmiany kategorii. W takim układzie musimy użytkownikowi przydzielić i tak uprawnienia do zapisu. Moim zdaniem najlepszym wyjściem jest przydzielanie praw do konkretnej, nazwanej akcji.
sobstel
Cytat(splatch @ 2005-12-19 09:37:11)
Moim zdaniem najlepszym wyjściem jest przydzielanie praw do konkretnej, nazwanej akcji.

tez tak uwazam, jednak widze jeden problem. np. system newsow, ktos moze dodawac newsy, ale edytowac moglby tylko swoje newsy (te ktore sam dodal) - wtedy nie mozna dac mu praw news_edit bo bedzie mogl wszystkie edytowac. na razie nie mam pomyslu jak to rozwiazac, poza wprowadzeniem jakichs parametrow - np. przydzielamy uprawnienia news_edit z parametrem only_own, parametr przekazywany do akcji i akcja wie jak sie zachowac, ale nie jest to rozwiazanie idealne dla mnie i troche komplikuje sprawe.
NuLL
Cytat
ta ta tabela z rolami jest to chrzanu.
wlasnie o to chodzi ze wszsytko ma byc elastyczne. wchodzi admin, dodaje nowa role i to ma dzialac. wywala role i ma dzialac. itd.

Uzyskanie czegos takiego jest wg mnie niemozliwe. Jesli jest chcialbym zobaczyc dzialajacy przyklad a nie slowa - implementujmy to co jest mozliwe do napisania a nie rzeczy z kosmosu.

Ja tabele z rolami mam ale u mnie to wyglada inaczej. W danych usera jest lista uprawnien jakie on posiada. Uprawnienia sa jako idki uprawnien w tabeli roles i tyle. Calosc systemu mozna zmienic aby konkretna role pobieral tylko wtedy kiedy ja trzeba sprawdzic. Pozatym mam klase accessParameter w ktorej moga sobie zdefiniowac nazwe zmiennej oraz jej zakres dla danego usera - i w ten sposob user moze edytowac newsy w konkrentej kategorii. Ja mam w systemie tez podstawowe akcje jak to sie jest prosto nazywa CRUD (create, read, update ,delete) plus akcje do obiektow wlasnego autorstwa. Reszta chodzi dzieki temu co jest wyzej.
bela
Ja tam wiem jak to rozwiązać winksmiley.jpg
Mamy sobie globalny filtr, który sprawdza role dla akcji - ok, ale to czasem nie wystarcza. Co wtedy? Dodajemy drugi filtr pod konkretną akcje, który to sprawdza czy user może mieć dostęp np. do danej kategorii.

Może trochę na około, ale chyba najlepsze rozwiązanie.
Ludvik
Cytat
Cytat

ta ta tabela z rolami jest to chrzanu.
wlasnie o to chodzi ze wszsytko ma byc elastyczne. wchodzi admin, dodaje nowa role i to ma dzialac. wywala role i ma dzialac. itd.


Uzyskanie czegos takiego jest wg mnie niemozliwe. Jesli jest chcialbym zobaczyc dzialajacy przyklad a nie slowa - implementujmy to co jest mozliwe do napisania a nie rzeczy z kosmosu.


A dlaczego miało by to być niemożliwe? Od tego mamy bazę, przejrzystą jej budowę i składnię, którą stosujemy do opisu ról, aby można było łatwo operować na danych. Role mamy od tego, żeby nie mieszać w kodzie aby opisać wymagania do uzyskania dostępu. Grupy po to, aby nie nadpisywać ról każdego użytkownika po kolei. Szkoda, że nie mogę ci przedstawić żadnego kodu, bo czas mi na to nie pozwala, ale pracuję nad tym. Można na święta coś będzie gotowe.

Sopel: Ten przypadek jest o tyle nieciekawy, że trzeba porównać w jakiś sposób id użytkownika i identyfikator autora newsa. Ja swój pomysł opisywałem na poprzedniej stronie tematu i wydaje mi się, że jest to najprostsza metoda wybrnięcia z problemu. Obiekty pomocnicze nie stanowią ani problemu wydajności, ani wzrostu złożoności aplikacji. W twoim rozwiązaniu musimy dopuścić użytkownika do akcji, nawet jeśli nie ma prawa do jej wykonania - przecież musimy jakoś sprawdzić czy jest autorem. U mnie tym zajmuje się ten obiekt pomocniczy (dla wygody można go nazwać ActionPrefetcher czy coś w tym stylu). Wczytujemy newsa, sprawdzamy wszystko co trzeba, a samą wiadomość zapisujesz gdzieś. Wychodzę z założenia, że największym złem jest dopuszczanie akcji do zabawy w uprawnienia. Właśnie to rozwiązanie wraz z rolami parametryzowanymi pozwala mi na osiągnięcie tego celu. Dokładniejszy opis jak mówiłem - trochę wcześniej w temacie.

Bela666: Jesteś najbliżej mojego pomysłu, chociaż sam przyznałeś, że to trochę na około. Różnica polega na tym, że ty masz filtr, który sprawdza specjalne uprawnienia. Ja pozostawiam sprawdzanie uprawnień głównemu filtrowi autoryzującemu, ale daję możliwość nadania użytkownikowi specjalnych ról/parametrów przed nadaniem prawa dostępu. Poza tym mój obiekt będzie trochę lżejszy smile.gif
sobstel
hmmm, przyznam ze do konca nie przemawia do mnie, a raczej nie do onca rozumiem idee tych obiekcikow jakby to mialo dzialac. ja bardziej myslalem juz np. o umieszczeniu w kazdej akcji metody (moze nawwet statycznej, zeby nie wywolywac akcji) access do ktorej przekazywane by byly odpowiednie argumenty i ona by zwracala true lub false.
Ludvik
Nie chodzi o samo wywoływanie akcji, ale dostęp do niej. Poza tym rozwalając metody autoryzujące po nie wiadomo jakiej liczbie klas zwiększasz prawdopodobieństwo wystąpienia błędu, a w przypadku kontroli dostępu jest to problem krytyczny. Poza tym wywołanie metod statycznych w dynamicznym konktekście (nazwa akcji jest znana dopiero podczas wykonywania programu) jest nieeleganckie i na pewno nie polepsza jakości kodu.

Wyobraź sobie tą sytuację z własnymi newsami...
Użytkownik posiada rolę editNews, ale akcja wymaga od niej jeszcze parametru "OWN". Kontroler autoryzacji nie wie w jaki sposób ma "zdobyć" ten parametr - on zna tylko statyczne, które są zapisane do bazy. Akcja podpowiada, że obiekt pomocniczy będzie wiedział co zrobić w tej sytuacji. Kontroler tworzy instancję klasy pomocniczej, a następnie prosi ją o wykonanie niezbędnych kroków. W tym przypadku obiekt pomocniczy wyciąga wiadomość z bazy, porównuje identyfikator użytkownika z identyfikatorem autora. Jeżeli wszystko się zgadza, to dopisywany jest parametr "OWN" do roli editNews. Dalsza część jest standardowa - sprawdzamy czy role się pokrywają i stwierdzamy, czy użytkownik może wywołać akcję. Zauważ, że kod klasy pomocniczej będzie miał zaledwie kilka linijek, a jego wykonanie będzie prawie niezauważalne pod względem wydajności (pomijając czas zapytania do bazy... ale przecież newsa nie trzeba pobierać drugi raz, dlatego można przechować go gdzieś, aby uniknąć ponownego wywołania tego samego zapytania).
bela
Cytat(Ludvik @ 2005-12-19 18:20:21)
Bela666: Jesteś najbliżej mojego pomysłu, chociaż sam przyznałeś, że to trochę na około. Różnica polega na tym, że ty masz filtr, który sprawdza specjalne uprawnienia. Ja pozostawiam sprawdzanie uprawnień głównemu filtrowi autoryzującemu, ale daję możliwość nadania użytkownikowi specjalnych ról/parametrów przed nadaniem prawa dostępu. Poza tym mój obiekt będzie trochę lżejszy smile.gif

Nie sądzę, filtr sprawdzający role to góra 20 linijek. Długość drugiego jest uwarunkowana stopniem złożoności schematu autoryzacji.
Ludvik
Z tą różnicą, że znowu musisz się bawić w porównania, a ja to robię tylko raz. Pomijając fakt, że filtr autoryzujący tak czy innaczej już istnieje. Trudno dyskutować bez przykładów czy schematów, a ja mi niestety czas nie pozwala, aby zrobić to w jeden-dwa dni :/ Więc jak będę już coś miał zrobione to opiszę to tutaj.
eai
Ja rozwiązałem całość w ten sposób.

tabela groups
Kod
group_id | group_name | group_permission | group_description


tabela user_groups
Kod
id | user_id | group_id


pole group_permission to zserializowana tablica z prawami dostępu. Jeśli klucz nie istnieje w tablicy oznacza to brak dostepu.
Kazdy user moze nalezec do kazdej grupy (jego prawa dostepu lacza sie w jedna tablice)

Zmiana uprawnien to operacje na tablicy wiec jest latwosc wprowadzania zmian, usuwania itd.
Mozna latwo napisac zapytanie przenoszenia userow z jednej grupy do drugiej itp (oczywiscie odpowiednie zapytanie, zeby usuwac tych co juz sa w danej grupie)

Dla mnie rozwiazanie jest proste i daje duzo mozliwosci.
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2024 Invision Power Services, Inc.