Warden
1.x
Docs/Warden/Plugin System
Open

Reading4 min
Updated31 Jul 2026
Sourcev1/integration/plugin-system.mdx

Warden's plugin system lets you hook into lifecycle events for audit logging, metrics, and custom behavior.

Base Interface01

Every plugin must implement the Plugin interface:

import "github.com/xraph/warden/plugin"

type Plugin interface {
    Name() string
}

Lifecycle Hooks02

Plugins opt into hooks by implementing additional interfaces:

Authorization Hooks

type BeforeCheck interface {
    BeforeCheck(ctx context.Context, req *warden.CheckRequest)
}

type AfterCheck interface {
    AfterCheck(ctx context.Context, req *warden.CheckRequest, result *warden.CheckResult)
}

Role Hooks

type RoleCreated interface {
    OnRoleCreated(ctx context.Context, r *role.Role)
}
type RoleUpdated interface {
    OnRoleUpdated(ctx context.Context, r *role.Role)
}
type RoleDeleted interface {
    OnRoleDeleted(ctx context.Context, roleID id.RoleID)
}

Permission Hooks

type PermissionCreated interface {
    OnPermissionCreated(ctx context.Context, p *permission.Permission)
}
type PermissionDeleted interface {
    OnPermissionDeleted(ctx context.Context, permID id.PermissionID)
}
type PermissionAttached interface {
    OnPermissionAttached(ctx context.Context, roleID id.RoleID, permID id.PermissionID)
}
type PermissionDetached interface {
    OnPermissionDetached(ctx context.Context, roleID id.RoleID, permID id.PermissionID)
}

Assignment Hooks

type RoleAssigned interface {
    OnRoleAssigned(ctx context.Context, a *assignment.Assignment)
}
type RoleUnassigned interface {
    OnRoleUnassigned(ctx context.Context, a *assignment.Assignment)
}

Relation Hooks

type RelationWritten interface {
    OnRelationWritten(ctx context.Context, t *relation.Tuple)
}
type RelationDeleted interface {
    OnRelationDeleted(ctx context.Context, objectType, objectID, rel, subjectType, subjectID string)
}

Policy Hooks

type PolicyCreated interface {
    OnPolicyCreated(ctx context.Context, p *policy.Policy)
}
type PolicyUpdated interface {
    OnPolicyUpdated(ctx context.Context, p *policy.Policy)
}
type PolicyDeleted interface {
    OnPolicyDeleted(ctx context.Context, policyID id.PolicyID)
}

Shutdown Hook

type Shutdown interface {
    OnShutdown(ctx context.Context) error
}

Registering Plugins03

eng, _ := warden.NewEngine(
    warden.WithStore(store),
    warden.WithPlugin(&MyAuditPlugin{}),
    warden.WithPlugin(&MyMetricsPlugin{}),
)

Type-Assertion Discovery04

The plugin registry uses type assertions to discover which hooks each plugin implements. You only need to implement the hooks you care about:

type MyPlugin struct{}

func (p *MyPlugin) Name() string { return "my-plugin" }

// Only implement AfterCheck — other hooks are ignored
func (p *MyPlugin) AfterCheck(ctx context.Context, req *warden.CheckRequest, result *warden.CheckResult) {
    log.Printf("check: %s %s %s%v", req.Subject.ID, req.Action, req.ResourceType, result.Allowed)
}

Built-in Plugins05

Chronicle Audit Plugin

Emits authorization events to Chronicle:

import "github.com/xraph/warden/audit_hook"

auditPlugin := audit_hook.New(chronicleClient)
eng, _ := warden.NewEngine(
    warden.WithStore(store),
    warden.WithPlugin(auditPlugin),
)

Events emitted:

  • warden.check.allowed / warden.check.denied

  • warden.role.created / warden.role.updated / warden.role.deleted

  • warden.permission.created / warden.permission.deleted

  • warden.assignment.created / warden.assignment.deleted

  • warden.relation.written / warden.relation.deleted

  • warden.policy.created / warden.policy.updated / warden.policy.deleted

Prometheus Metrics Plugin

Exports authorization metrics:

import "github.com/xraph/warden/observability"

metricsPlugin := observability.New()
eng, _ := warden.NewEngine(
    warden.WithStore(store),
    warden.WithPlugin(metricsPlugin),
)

Counters:

  • warden_checks_total — Total authorization checks by result

  • warden_check_duration_seconds — Check latency histogram

  • warden_mutations_total — Entity mutations by type and operation