Aller au contenu principal

Adaptateurs

Casbin charge et sauvegarde la politique via des adapters. L'enforcer appelle LoadPolicy() pour charger les règles et, lorsque c'est supporté, SavePolicy() pour les persister. Les adapters sont implémentés dans des packages séparés pour garder la bibliothèque principale légère.

Adaptateurs supportés​

Les adaptateurs par langage sont listés ci-dessous. Pour ajouter un adaptateur tiers, ouvrez une issue ou une PR.

Adapter Type Author AutoSave Description
File Adapter (built-in) File Casbin ❌ For .CSV (Comma-Separated Values) files
Filtered File Adapter (built-in) File @faceless-saint ❌ For .CSV (Comma-Separated Values) files with policy subset loading support
SQL Adapter SQL @Blank-Xu ✅ MySQL, PostgreSQL, SQL Server, SQLite3 are supported in master branch and Oracle is supported in oracle branch by database/sql
Xorm Adapter ORM Casbin ✅ MySQL, PostgreSQL, TiDB, SQLite, SQL Server, Oracle are supported by Xorm
GORM Adapter ORM Casbin ✅ MySQL, PostgreSQL, Sqlite3, SQL Server are supported by GORM
GORM Adapter Ex ORM Casbin ✅ MySQL, PostgreSQL, Sqlite3, SQL Server are supported by GORM
Ent Adapter ORM Casbin ✅ MySQL, MariaDB, PostgreSQL, SQLite, Gremlin-based graph databases are supported by ent ORM
Beego ORM Adapter ORM Casbin ✅ MySQL, PostgreSQL, Sqlite3 are supported by Beego ORM
SQLX Adapter ORM @memwey ✅ MySQL, PostgreSQL, SQLite, Oracle are supported by SQLX
Sqlx Adapter ORM @Blank-Xu ✅ MySQL, PostgreSQL, SQL Server, SQLite3 are supported in master branch and Oracle is supported in oracle branch by sqlx
GF ORM Adapter ORM @vance-liu ✅ MySQL, SQLite, PostgreSQL, Oracle, SQL Server are supported by GoFrame ORM
GoFrame ORM Adapter ORM @kotlin2018 ✅ MySQL, SQLite, PostgreSQL, Oracle, SQL Server are supported by GoFrame ORM
gf-adapter ORM @zcyc ✅ MySQL, SQLite, PostgreSQL, Oracle, SQL Server are supported by GoFrame ORM
Gdb Adapter ORM @jxo-me ✅ MySQL, SQLite, PostgreSQL, Oracle, SQL Server are supported by GoFrame ORM
GoFrame V2 Adapter ORM @hailaz ✅ MySQL, SQLite, PostgreSQL, Oracle, SQL Server are supported by GoFrame ORM
Bun Adapter ORM @JunNishimura ✅ MySQL, SQLite, PostgreSQL, SQL Server are supported by Bun ORM
Filtered PostgreSQL Adapter SQL Casbin ✅ For PostgreSQL
Filtered pgx Adapter SQL @pckhoi ✅ PostgreSQL is supported by pgx
Pgx Adapter SQL @gtoxlili ✅ PostgreSQL is supported by pgx, supports customizable column count
casbin-pgx-adapter SQL @noho-digital ✅ A PostgreSQL adapter for Casbin using the pgx driver.
PostgreSQL Adapter SQL @cychiuae ✅ For PostgreSQL
RQLite Adapter SQL EDOMO Systems ✅ For RQLite
MongoDB Adapter NoSQL Casbin ✅ For MongoDB based on MongoDB Go Driver
RethinkDB Adapter NoSQL @adityapandey9 ✅ For RethinkDB
Cassandra Adapter NoSQL Casbin ❌ For Apache Cassandra DB
DynamoDB Adapter NoSQL HOOQ ❌ For Amazon DynamoDB
Dynacasbin NoSQL NewbMiao ✅ For Amazon DynamoDB
ArangoDB Adapter NoSQL @adamwasila ✅ For ArangoDB
Amazon S3 Adapter Cloud Soluto ❌ For Minio and Amazon S3
Go CDK Adapter Cloud @bartventer ✅ Adapter based on Go Cloud Dev Kit that supports: Amazon DynamoDB, Azure CosmosDB, GCP Firestore, MongoDB, In-Memory
Azure Cosmos DB Adapter Cloud @spacycoder ✅ For Microsoft Azure Cosmos DB
GCP Firestore Adapter Cloud @reedom ❌ For Google Cloud Platform Firestore
GCP Cloud Storage Adapter Cloud qurami ❌ For Google Cloud Platform Cloud Storage
GCP Cloud Spanner Adapter Cloud @flowerinthenight ✅ For Google Cloud Platform Cloud Spanner
Consul Adapter KV store @ankitm123 ❌ For HashiCorp Consul
Redis Adapter (Redigo) KV store Casbin ✅ For Redis
Redis Adapter (go-redis) KV store @mlsen ✅ For Redis
Etcd Adapter KV store @sebastianliu ❌ For etcd
BoltDB Adapter KV store @speza ✅ For Bolt
Bolt Adapter KV store @wirepair ❌ For Bolt
BadgerDB Adapter KV store @inits ✅ For BadgerDB
Protobuf Adapter Stream Casbin ❌ For Google Protocol Buffers
JSON Adapter String Casbin ❌ For JSON
String Adapter String @qiangmzsx ❌ For String
HTTP File Adapter HTTP @h4ckedneko ❌ For http.FileSystem
FileSystem Adapter File @naucon ❌ For fs.FS and embed.FS
NATS JetStream Adapter KV store grepplabs ✅ For NATS JetStream
Kubernetes Adapter Cloud grepplabs ✅ For Kubernetes
remarque
  1. Lorsque vous appelez casbin.NewEnforcer() avec un adaptateur (explicite ou implicite), les politiques sont chargées automatiquement.
  2. Appelez e.LoadPolicy() pour rafraîchir les politiques depuis le stockage.
  3. Sans support Auto-Save, les adaptateurs ne peuvent pas persister automatiquement les modifications de politique lorsque vous modifiez les politiques. Appelez SavePolicy() manuellement pour persister toutes les règles.

Exemples​

Plusieurs exemples d'utilisation d'adaptateurs suivent :

Adaptateur de fichier (intégré)​

Initialiser un enforcer en utilisant l'adaptateur de fichier intégré :

import "github.com/casbin/casbin/v3"

e := casbin.NewEnforcer("examples/basic_model.conf", "examples/basic_policy.csv")

Alternative équivalente :

import (
"github.com/casbin/casbin/v3"
fileadapter "github.com/casbin/casbin/v3/persist/file-adapter"
)

a := fileadapter.NewAdapter("examples/basic_policy.csv")
e := casbin.NewEnforcer("examples/basic_model.conf", a)

Adaptateur MySQL​

Initialiser un enforcer en utilisant une connexion à une base de données MySQL sur 127.0.0.1:3306 avec l'utilisateur root et sans mot de passe :

import (
"github.com/casbin/casbin/v3"
"github.com/casbin/mysql-adapter"
)

a := mysqladapter.NewAdapter("mysql", "root:@tcp(127.0.0.1:3306)/")
e := casbin.NewEnforcer("examples/basic_model.conf", a)

Utiliser votre propre adaptateur de stockage​

Intégrer un adaptateur personnalisé :

import (
"github.com/casbin/casbin/v3"
"github.com/your-username/your-repo"
)

a := yourpackage.NewAdapter(params)
e := casbin.NewEnforcer("examples/basic_model.conf", a)

Migrer/Convertir entre différents adaptateurs​

Pour migrer les politiques de l'adaptateur A vers l'adaptateur B :

  1. Charger la politique de A en mémoire
e, _ := NewEnforcer(m, A)

ou

e.SetAdapter(A)
e.LoadPolicy()
  1. Passer de l'adaptateur A à B
e.SetAdapter(B)
  1. Sauvegarder la politique depuis la mémoire vers B
e.SavePolicy()

Chargement/Sauvegarde à l'exécution​

Recharger les modèles et les politiques ou persister les modifications de politique après l'initialisation :

// Reload the model from the model CONF file.
e.LoadModel()

// Reload the policy from file/database.
e.LoadPolicy()

// Save the current policy (usually after changed with Casbin API) back to file/database.
e.SavePolicy()

AutoSave​

Les adaptateurs avec la fonctionnalité Auto-Save peuvent persister des modifications individuelles de politique directement dans le stockage sans opération de sauvegarde complète. Cela diffère de SavePolicy(), qui efface le stockage et réécrit toutes les politiques, ce qui peut entraîner des problèmes de performance avec de grands ensembles de politiques.

Lorsqu'un adaptateur prend en charge Auto-Save, contrôlez ce comportement via Enforcer.EnableAutoSave(). Cette option est activée par défaut pour les adaptateurs compatibles.

remarque
  1. Auto-Save est une fonctionnalité facultative. Les adaptateurs peuvent l'implémenter ou non.
  2. Auto-Save ne fonctionne que si l'adaptateur du moteur d'application (enforcer) le prend en charge.
  3. Vérifiez la colonne AutoSave dans la liste des adaptateurs ci-dessus pour déterminer la prise en charge.

Exemple d'utilisation d'Auto-Save :

import (
"github.com/casbin/casbin/v3"
"github.com/casbin/xorm-adapter"
_ "github.com/go-sql-driver/mysql"
)

// AutoSave is enabled by default when using compatible adapters with enforcers.
a := xormadapter.NewAdapter("mysql", "mysql_username:mysql_password@tcp(127.0.0.1:3306)/")
e := casbin.NewEnforcer("examples/basic_model.conf", a)

// Disable AutoSave.
e.EnableAutoSave(false)

// Policy changes affect only the in-memory enforcer,
// not the storage.
e.AddPolicy(...)
e.RemovePolicy(...)

// Enable AutoSave.
e.EnableAutoSave(true)

// Policy changes now persist to storage
// in addition to updating the in-memory enforcer.
e.AddPolicy(...)
e.RemovePolicy(...)

Exemples supplémentaires : https://github.com/apache/casbin-xorm-adapter/blob/master/adapter_test.go

Comment écrire un adaptateur​

Implémentez l'interface Adapter avec au moins deux méthodes requises : LoadPolicy(model model.Model) error et SavePolicy(model model.Model) error.

Trois méthodes facultatives permettent la prise en charge d'Auto-Save.

MéthodeTypeDescription
LoadPolicy()obligatoireCharger toutes les règles de politique depuis le stockage
SavePolicy()obligatoireSauvegarder toutes les règles de politique dans le stockage
AddPolicy()facultatifAjouter une règle de politique au stockage
RemovePolicy()facultatifSupprimer une règle de politique du stockage
RemoveFilteredPolicy()facultatifSupprimer du stockage les règles de politique correspondant au filtre
remarque

Lorsqu'un adaptateur ne prend pas en charge Auto-Save, fournissez des implémentations vides pour les trois méthodes facultatives. Exemple en Golang :

// AddPolicy adds a policy rule to the storage.
func (a *Adapter) AddPolicy(sec string, ptype string, rule []string) error {
return errors.New("not implemented")
}

// RemovePolicy removes a policy rule from the storage.
func (a *Adapter) RemovePolicy(sec string, ptype string, rule []string) error {
return errors.New("not implemented")
}

// RemoveFilteredPolicy removes policy rules that match the filter from the storage.
func (a *Adapter) RemoveFilteredPolicy(sec string, ptype string, fieldIndex int, fieldValues ...string) error {
return errors.New("not implemented")
}

Les moteurs d'application Casbin ignorent l'erreur "not implemented" lors de l'appel de ces méthodes facultatives.

Exigences relatives à l'implémentation de l'adaptateur :

  • Structure de données. Prendre en charge la lecture d'au moins six colonnes.
  • Nom de la base de données. Par défaut casbin.
  • Nom de la table. Par défaut casbin_rule.
  • Colonne Ptype. Nommée ptype (et non p_type ou Ptype).
  • Définition de la table : (id int primary key, ptype varchar, v0 varchar, v1 varchar, v2 varchar, v3 varchar, v4 varchar, v5 varchar).
  • Index de clé unique : Construit sur les colonnes ptype,v0,v1,v2,v3,v4,v5.
  • LoadFilteredPolicy accepte un paramètre de filtre structuré comme suit :
{
"p": ["", "domain1"],
"g": ["", "", "domain1"]
}

Qui est responsable de la création de la BD ?​

Par convention, les adaptateurs doivent créer automatiquement une base de données casbin si elle n'existe pas et l'utiliser pour le stockage des politiques. Implémentation de référence : https://github.com/apache/casbin-xorm-adapter

UpdateAdapter​

L'interface UpdateAdapter étend l'interface Adapter de base pour permettre des mises à jour directes des politiques dans le stockage. Cette approche est plus efficace que la séquence suppression-ajout lors de la modification de règles existantes.

Les adaptateurs implémentant UpdateAdapter fournissent ces méthodes :

MéthodeTypeDescription
UpdatePolicy()facultatifMettre à jour une seule règle de politique dans le stockage
UpdatePolicies()facultatifMettre à jour plusieurs règles de politique dans le stockage
UpdateFilteredPolicies()facultatifMettre à jour dans le stockage les règles de politique correspondant au filtre

Exemple​

Mettre à jour l'utilisation de l'adaptateur :

import (
"github.com/casbin/casbin/v3"
"github.com/casbin/gorm-adapter/v3"
)

a, _ := gormadapter.NewAdapter("mysql", "root:@tcp(127.0.0.1:3306)/")
e, _ := casbin.NewEnforcer("examples/rbac_model.conf", a)

// Update a single policy
// Change: p, alice, data1, read -> p, alice, data1, write
e.UpdatePolicy(
[]string{"alice", "data1", "read"},
[]string{"alice", "data1", "write"},
)

// Update multiple policies at once
e.UpdatePolicies(
[][]string{{"alice", "data1", "write"}, {"bob", "data2", "read"}},
[][]string{{"alice", "data1", "read"}, {"bob", "data2", "write"}},
)

// Update all policies matching a filter
e.UpdateFilteredPolicies(
[][]string{{"alice", "data1", "write"}},
0,
"alice", "data1", "read",
)

Comment écrire un adaptateur de mise à jour​

Pour implémenter UpdateAdapter, ajoutez les méthodes de mise à jour à votre implémentation de base d'Adapter :

// UpdatePolicy updates a policy rule from storage.
// This is part of the UpdateAdapter interface.
func (a *Adapter) UpdatePolicy(sec string, ptype string, oldRule, newRule []string) error {
// Update the policy in storage
// SQL example: UPDATE casbin_rule SET v0=?, v1=?, v2=? WHERE ptype=? AND v0=? AND v1=? AND v2=?
return nil
}

// UpdatePolicies updates multiple policy rules in the storage.
// This is part of the UpdateAdapter interface.
func (a *Adapter) UpdatePolicies(sec string, ptype string, oldRules, newRules [][]string) error {
// Update multiple policies in storage
// Use transactions for consistency
return nil
}

// UpdateFilteredPolicies updates policy rules that match the filter from the storage.
// This is part of the UpdateAdapter interface.
func (a *Adapter) UpdateFilteredPolicies(sec string, ptype string, newRules [][]string, fieldIndex int, fieldValues ...string) error {
// Find policies matching the filter, then update them
return nil
}
remarque

Sans support d'UpdateAdapter, Casbin revient automatiquement à combiner les opérations RemovePolicy() et AddPolicy().

Adaptateur Contexte​

ContextAdapter fournit des opérations sensibles au contexte pour les adaptateurs Casbin.

Le contexte permet des fonctionnalités telles que le contrôle du délai d'expiration pour les appels API de l'adaptateur.

Exemple​

gormadapter prend en charge le contexte. Voici un exemple de contrôle du délai d'expiration utilisant le contexte :

ca, _ := NewContextAdapter("mysql", "root:@tcp(127.0.0.1:3306)/", "casbin")
// Set 300s timeout
ctx, cancel := context.WithTimeout(context.Background(), 300*time.Microsecond)
defer cancel()

err := ca.AddPolicyCtx(ctx, "p", "p", []string{"alice", "data1", "read"})
if err != nil {
panic(err)
}

Comment écrire un adaptateur de contexte​

L'API ContextAdapter ajoute une couche de traitement du contexte par-dessus l'API standard Adapter. Après avoir implémenté l'API Adapter standard, enveloppez votre logique avec la gestion du contexte.

Implémentation de référence : adapter.go

Transaction​

Casbin prend en charge les transactions. Utilisation des transactions dans gormadapter :

db, _ := gorm.Open(...)
adapter, _ := gormadapter.NewTransactionalAdapterByDB(db)
e, _ := casbin.NewTransactionalEnforcer("examples/rbac_model.conf", adapter)

ctx := context.Background()

// WithTransaction executes a function within a transaction.
// Errors trigger rollback; otherwise, automatic commit occurs.
err := e.WithTransaction(ctx, func(tx *casbin.Transaction) error {
tx.AddPolicy("alice", "data1", "read")
tx.AddPolicy("alice", "data1", "write")
return nil
})

// Manual transaction handling
tx, _ := e.BeginTransaction(ctx)
tx.AddPolicy("alice", "data1", "write")
if err := tx.Commit(); err != nil {
// handle transaction failure
}

Implémentez TransactionalAdapter et TransactionContext depuis persist/transaction.go pour ajouter le support des transactions.

Référence : adapter.go

Comments are powered by giscus and GitHub Discussions. They load from giscus.app and GitHub only after you click the button below.