Esempio di procedura guidata utilizzando la libreria di controllo dell'accesso con filtro
In questo argomento vengono forniti alcuni esempi di utilizzo della libreria e del codice concatenato. Questi esempi presuppongono che la funzione Init()
sia stata chiamata per creare le entità bootstrap e che il chiamante di Init()
e invoke()
sia "%CN%frank.thomas@example.com"
. Il flusso normale in un'applicazione consiste nel creare alcune liste di controllo dell'accesso iniziali che verranno utilizzate per concedere o negare l'accesso alle altre entità.
Inizializzazione
Chiamare la funzione Initialization()
per creare entità di bootstrap durante la distribuzione dei codici concatenati. Ad esempio:
import "chaincodeACL"
func (t \*SimpleChaincode) Init(nil, stub shim.ChaincodeStubInterface) pb.Response
{
err := chaincodeACL.Initialization(stub)
}
Creazione di un ACL
import "chaincodeACL"
...
{
**ACLMgr** := chaincodeACL.NewACLManager(nil, stub) // Not specify identity, use caller's identity as default.
// Define a new ACL
**newACL** := chaincodeACL.ACL{
"AllowAdmins", // ACL name
"Allow administrators full access", // Description
[]string{"CREATE","READ","UPDATE","DELETE"}, // Accesses allowed or not
true, // Allowed
[]string{"%CN%bob.dole@example.com","%OU%example.com,"%GRP%admins"}, // Initial identity patterns
".ACLs.acl", // Start with bootstrap ACL
}
// Add this ACL with default identity (caller's identify here)
err := **ACLMgr**.Create( **newACL** , nil)
}
È possibile utilizzare la nuova ACL per modificare gli utenti che possono eseguire determinate operazioni. In primo luogo, aggiungere questa nuova ACL al gruppo di bootstrap .Groups
per consentire a qualsiasi amministratore di creare un gruppo.
Aggiungi un'ACL a un gruppo
import "chaincodeACL"
…
{
**groupMgr** := chaincodeACL.NewGroupManager(nil, stub) // Not specify identity, use caller's identity as default.
err := **groupMgr**.AddAfterACL(
".Groups", // Bootstrap group name
".Groups.ACL", // Which ACL to add after
"AllowAdmins", // The new ACL to add
nil // with default identity that's frank.thomas
)
}
In questo modo l'ACL AllowAdmins
viene aggiunta al gruppo bootstrap .Groups
dopo l'ACL bootstrap iniziale. Ciò garantisce che Frank Thomas possa ancora completare le operazioni sul gruppo .Groups
perché l'ACL che concede l'autorizzazione Frank è la prima nell'elenco. Ora, chiunque corrisponda all'ACL AllowAdmins
può completare le operazioni CREATE, READ, UPDATE o DELETE (ora possono creare gruppi).
Creare un gruppo
Gli amministratori ora possono creare un gruppo.
import "chaincodeACL"
...
{
...
// Define a new group.
**newGroup** := chaincodeACL.Group{
"AdminGrp", // Name of the group
"Administrators of the app", // Description of the group
{"%CN%jill.muller@example.com","%CN%ivan.novak@example.com","%ATTR%role=admin"},
[]string{"AllowAdmins"}, // The ACL for the group
}
**groupMgr** := chaincodeACL.NewGroupManager(nil, stub) // Not specify identity, use caller's identity as default.
err := **groupMgr**.Create( **newGroup** , bob\_garcia\_certificate) // Using a specific certificate
...
}
Questa chiamata utilizza un'identità esplicita (Bob Garcia, utilizzando il suo certificato) per tentare di creare un gruppo. Poiché Bob Garcia corrisponde a un pattern nell'ACL AllowAdmins
e i membri di tale ACL possono eseguire operazioni CREATE sul gruppo bootstrap .Groups
, questa chiamata avrà esito positivo. Se Jim Silva, che non era nell'unità organizzativa example.com
né nel gruppo AdminGrp
(che ancora non esiste), avesse passato il suo certificato come ultimo argomento, la chiamata non sarebbe riuscita in quanto non dispone delle autorizzazioni appropriate. Questa chiamata crea un gruppo denominato "AdminGrp
" con i membri iniziali del gruppo jill.muller@example.com e ivan.novak@example.com o chiunque disponga del ruolo attributo (ABAC) role=admin.
Crea una risorsa
import "chaincodeACL"
...
{
...
**newResource** := **chaincodeACL**.Resource{
"transferMarble", // Name of resource to create
"The transferMarble chaincode function", // Description of the resource
[]string{"AllowAdmins"}, // Single ACL for now allowing administrators
}
**resourceMgr** := **chaincodeACL**.NewResourceManager(nil, stub) // Not specify identity, use caller's identity as default.
err := **resourceMgr**.Create(resourceMgr, nil) // Using caller's certificate
...
}
In questo modo viene creata una risorsa denominata transferMarble
che l'applicazione potrebbe utilizzare per controllare l'accesso alla funzione chaincode transferMarble
. L'accesso è attualmente limitato dalla lista di controllo dell'accesso AllowAdmins
.
Controllare l'accesso per una risorsa
È possibile utilizzare questa nuova risorsa nel codice concatenato per consentire solo agli amministratori di trasferire un marmo, modificando il metodo invoke()
del codice concatenato Marmi come mostrato nel seguente codice:
import "chaincodeACL"
…
func (t \*SimpleChaincode) Invoke(stub shim.ChaincodeStubInterface) pb.Response {
**resourceMgr** := **chaincodeACL**.NewResourceManager(nil, stub) // Not specify identity, use caller's identity as default.
function, args := stub.GetFunctionAndParameters()
fmt.Println("invoke is running " + function) // Handle different functions
if function == "initMarble" { //create a marble
return t.initMarble(stub, args)}
else if function == " **transferMarble**" { //change owner of a specific marble
**allowed** , err : = **resourceMgr**. **CheckAccess** ("transferMarble", "UPDATE", nil)
if **allowed** == true {
return t.transferMarble(stub, args)
else {
return NOACCESS
}
} else if function == "transferMarblesBasedOnColor" { //transfer all marbles of a certain color
…
}
}