Implementieren von ACL-Einschränkungen, mehr als Zulassen / Verweigern

8

Ich habe ein kleines, aber effektives MVC-Framework für die Verwendung in einer Anwendung entwickelt und implementiere eine ACL-Abfrage pro Anfrage.

Schnelle Details: PHP 5.3+; MySQL 5.1+; Benutzerdefiniertes Framework, "MVC-like"

Ab sofort ist die ACL-Prüfung einfach " verweigern-wenn-nicht-weiß-Auflistung "; Jedem group kann eine Berechtigung für bestimmte Anforderungshandler zugewiesen werden. Zum Beispiel:

%Vor%

( user und group sind der Kürze halber nicht enthalten, aber ihre Modelle sind nichts Ungewöhnliches )

Wie auch immer, mein Framework routet URIs über eine Handler / Pfadtabelle an die entsprechende handler_key (, um die Dateisystemarchitektur zu entkoppeln ). Die Anfrage wird dann an den Handler gesendet, wenn group_id zugeordnet ist mit der Anfrage ist für diesen handler_key in die weiße Liste gesetzt.

Ich bin neugierig, was ist der beste Ansatz zum Implementieren des Speicherns / Überprüfens beliebiger ( benutzerdefinierter ) Einschränkungen? Fallbeispiele wären:

  • Lassen Sie die angegebene Gruppe nur wochentags zwischen 8:00 und 17:00 Uhr einen Handler aufrufen.
  • Erlaube der angegebenen Gruppe nur, einen Handler aufzurufen, um "eigene" Daten zu ändern; dh: Daten, die von der zugehörigen user erstellt wurden. Diese Überprüfung würde vielleicht eine Überprüfung des user_id -Feldes beinhalten, das mit dem Inhalt verbunden ist, der vom Handler geändert werden soll, und des user_id , das mit der Anfrage verknüpft ist

Ich hatte eine flags -Spalte, aber das ist nicht zukunftssicher mit der Einführung von mehr Feature, Gruppe und Constraint-Anforderungen. Ich dachte in die folgende Richtung, aber was zu verwenden?

%Vor%

Unnötige Klarstellung:

( Hinweis: Code wurde hier eingegeben, nicht copypasta von Projekt )

Um etwas von dem Jargon hier zu klären; Handler (speziell Web-Handler) sind im Wesentlichen Controller für diejenigen, die mit dem MVC-Archetyp vertraut sind.

Ihre spezifische Implementierung ist eine einzelne PHP-Datei, die eine Funktion zurückgibt, die vom Dispatcher oder Sub-Handler-Aufrufer aufgerufen wird. Zum Beispiel:

%Vor%

Mein Framework verwendet Web-Handler und API-Handler ; Web-Handler füttern Daten in ein Antwortobjekt (im Grunde eine Sammlung hierarchischer Ansichten ), die HTML generieren. Die Daten werden durch Aufrufen der API-Handler abgerufen, die einfach Rohdaten zurückgeben (API-Handler könnten als Repräsentationen des Modells angesehen werden, die auf typische MVC zurückgehen)

Zusammengesetzte Handler sind im Wesentlichen eine Abstraktionsschicht, da sie selbst Handler sind, die Handler aufrufen, um Daten zu aggregieren. Meine aktuelle Implementierung der ACL-Prüfung führt eine kursorische Überprüfung aller verschachtelten Handler durch (via $meta , eine Array-Variable, die als Metadaten-Header für den Handler deklariert wurde). Beispiel:

%Vor%     
Dan 25.05.2011, 22:09
quelle

2 Antworten

2

Nachdem ich meine architektonischen Entscheidungen überprüft hatte, wurde mir klar, dass ich meinen handler style Request-Handling-Ansatz nutzen konnte.

( Bitte, kritisieren und / oder lächerlich machen und / oder diesen Vorschlag als gerechtfertigt ansehen

)

Eine Anfrage, um zu überprüfen, ob ein Benutzer über Berechtigungen verfügt, kann für diese Zwecke als einfach eine andere Anfrage angesehen werden und erfordert daher einen eigenen Handler . Zum Beispiel:

%Vor%

Durch das Hinzufügen einer Spalte NULL -able constraint_handler_key können neue Einschränkungen programmgesteuert erstellt und administrativ delegiert werden.

Wenn eine Anforderung ausgelöst wird, aggregiert das Framework die Handler-Kette und vergleicht sie mit der Whitelist, wie dies bereits der Fall ist. Falls ein constraint_handler_key existiert ( möglicherweise mit Argumenten, wie die obige Tabelle andeutet ), führt es eine Suche in der handlerTable durch, die mit diesem Anfragetyp verbunden ist:

%Vor%

( API-Handler sind ebenfalls identisch )

Es wird erwartet, dass der ACL-Handler nur boolesche Werte zurückgibt, wodurch die Berechtigungsüberprüfungssequenz und damit die gesamte Anfrage fortgesetzt oder beendet wird.

%Vor%

Fälle des Weglassens von constraint_handler_key s werden als einfache Whitelist-Prüfungen behandelt; allow-if / deny-if-not .

So sieht mein Anwendungsverzeichnis wie folgt aus:

%Vor%     
Dan 26.05.2011, 06:32
quelle
4

Das Video, das ich in meinem Kommentar gepostet habe, hat ähnliche Ideen wie die, die du geteilt hast, aber keinen Code.

In Bezug auf Ihre Frage habe ich das nie umgesetzt und ich habe nur eine vage Vorstellung, wie ein solches System gebaut werden könnte (oder nicht), also meine Eingabe mit einem (oder mehreren) Korn (en) übernehmen von Salz .

Als Erstes müssen Sie die Beschränkungen identifizieren, die der Benutzer einschränken kann. Dabei können Sie willkürliche Daten vergessen und definieren, was der Benutzer definieren kann und was nicht. Das ist der wichtigste Punkt hier.

Der nächste Schritt besteht darin, eine Art von Notation oder Datenstruktur zu definieren, die Sie leicht analysieren und validieren können, zum Beispiel haben Sie bei zeitbasierten Einschränkungen folgende Möglichkeiten:

  • bestimmte Datumsangaben (2011-05-26)
  • datetime ranges (2011-05-26 bis 2011-05-31)
  • rekursive Datumsangaben (201x-05-26 oder jeden Freitag)
  • logische (und / oder / xor) Operatoren

Wenn Sie eine korrekte Schreibweise haben, können Sie diese einfach analysieren und validieren, indem Sie die Regel in Token setzen und vielleicht mit etwas DatePeriod oder DateInterval oder sogar der Modulo-Operator wie crontab.

Ihr zweites Beispiel:

  

Lassen Sie nur die angegebene Gruppe zu   ein Handler, um "eigene" Daten zu ändern; zB:   Daten, die vom zugeordneten Benutzer erstellt wurden.

Klingt wie normale ACL für mich:

  • Ressource: spezifische Daten
  • role: spezifischer Benutzer

Dann haben Sie natürlich die komplizierteren Regeln wie:

  

Der Benutzer, der den Datensatz genehmigt, muss   haben ein gleiches oder höheres Niveau (in der   gleichen Sicherheits-Namespace) wie der Benutzer   wer hat die Platte erstellt, aber sie können nicht   sei der gleiche Benutzer.

Ich denke, dass diese Art von Regeln für die Anwendungslogik spezifisch sein müssen und eine echte universelle Lösung extrem schwierig zu implementieren wäre. Zed Shaw erwähnte in seinem Vortrag, dass er eine komplette Lösung entwickelt hat, die nur 400 Codezeilen verwendet. Ich wäre sehr interessiert daran zu erfahren, wie er das gemacht hat.

Flags (in Bits gespeichert) sind eine großartige (wenn auch kryptische) Möglichkeit, eine Kombination aus einem oder mehreren Constrains anzugeben, aber nach meiner Erfahrung ist es besser, wenn Sie alle Constrains apriori definieren.

Da Sie die Beschränkungen, die Sie überprüfen möchten, nicht genau zu kennen scheinen, empfehle ich Ihnen, Notationen für die verschiedenen Arten von Einschränkungen zu erstellen, die Sie überprüfen möchten:

  • zeitbasiert
  • benutzer- / ressourcenbasiert
  • ...

Und implementieren Sie dann Methoden, die analysieren (vielleicht mit einer Notation, die die Version impliziert, so dass Sie in der Zukunft migrieren können) und validieren Sie alle Einschränkungen.

Es tut mir leid, wenn meine Antwort nicht viel hilft, aber ich finde die Frage sehr interessant und ich hoffe, dass jemand anderes mit einem besseren auftaucht, AFAIK, es gibt keinen Zauberstab dafür.

    
Alix Axel 26.05.2011 02:17
quelle