Il metodo standard è un Elenco di controllo di accesso discrezionale (DACL) . Tale struttura mappa le entità (ad es. Utenti, gruppi di utenti, ecc.) In risorse (ad esempio file, mutex, socket, ecc.) Con un insieme definito di attributi di autorizzazione posizionati su ciascun collegamento.
Ad esempio, il seguente rappresenta un semplice DACL di lettura / scrittura:
Resource | Entity | R | W |
----------------+----------+---+---+
/foo/bar | Alice | 1 | 0 |
/foo/bar | Bob | 1 | 1 |
/bar/foo | Eve | 1 | 1 |
/log | Everyone | 0 | 1 |
/log | Alice | 1 | 1 |
In questo caso, Alice ha accesso in lettura a /foo/bar
e Bob ha accesso in lettura / scrittura a /foo/bar
, mentre Eve non ha accesso a /foo/bar
perché non ha voce nella tabella DACL. Solo Eve ha accesso a /bar/foo
.
Il caso interessante è quando guardiamo la risorsa /log
, a cui il gruppo Everyone ha accesso in scrittura. Dato che Alice è nel gruppo Everyone, immaginiamo che non dovrebbe aver bisogno di una voce, ma la sua voce sovrascrive le impostazioni del gruppo. A questo punto, abbiamo creato un DACL gerarchico , che ci consente di ereditare le autorizzazioni e fornire comportamenti di override specifici più bassi nella gerarchia.
Tale modello fornisce autorizzazioni estremamente flessibili e può essere implementato in una varietà di diversi sistemi di archiviazione dei dati, ad es. filesystem, RDBMS, motore di memorizzazione dei valori-chiave, ecc.
Ovviamente, l'esempio precedente non si traduce direttamente in una tabella di database relazionale, a causa dell'ambiguità tra gruppi di utenti e utenti. Questo può essere risolto utilizzando un identificatore di sicurezza (SID) , che identifica in modo univoco qualsiasi entità. Probabilmente lo implementerei qualcosa del genere:
TABLE resource_dacl
resource_id INTEGER NOT_NULL
security_id INTEGER NULL
perm_read TINYINT(1) DEFAULT 0 // permission to read the resource
perm_write TINYINT(1) DEFAULT 0 // permission to write to the resource
perm_delete TINYINT(1) DEFAULT 0 // permission to delete the resource
perm_acl TINYINT(1) DEFAULT 0 // permission to change the resource's ACL
...
PRIMARY_KEY ( resource_id, security_id )
Il security_id
dovrebbe essere univoco per ogni entità e dovrebbe essere memorizzato all'interno delle tabelle di utenti e gruppi di utenti.
Ciò consente di interrogare facilmente le autorizzazioni in SQL utilizzando un JOIN
con WHERE EXISTS
, risultante in un singolo valore dal database, contenente un 1 o 0 per indicare se i permessi richiesti sono impostati.