Skip to main content

Recursive Memberships and Permissions for the Education Warehouse Authentication System

Project description

edwh-auth-rbac

Role-Based Access Control (RBAC) library with recursive memberships for Python applications.

Overview

This library implements a comprehensive RBAC system that supports:

  • Users, groups, and items as identities
  • Recursive group memberships (groups can contain other groups)
  • Time-bound permissions with start/end dates
  • Wildcard permissions (* for all privileges, all identities, or all targets)
  • Password hashing with HMAC-SHA512 and per-entry random salts

Mental Model

The system is built around three core concepts:

  1. Identities: Users (people), Groups (collections), and Items (resources)
  2. Memberships: Direct relationships between identities (who belongs to what)
  3. Permissions: Granted privileges on targets with time constraints

Key Features

  • Recursive membership resolution through database views
  • Efficient permission checking using JOINs with recursive membership views
  • Flexible identity lookup by email, ID, UUID, or name
  • Secure password storage with constant-time validation

Installation

pip install edwh-auth-rbac

Basic Usage

This requires a setup like the demo, see below for details, but this is how you would mostly use it in every day use:

from pydal import DAL
from edwh_auth_rbac import AuthRbac

# Initialize database
db = DAL('sqlite://storage.sqlite')

# Initialize RBAC
rbac = AuthRbac(db)
rbac.define_model(allowed_types=['user', 'group', 'item'], migrate=True)

Creating Users and Groups

# Create a group
admin_group = rbac.add_group(
    email="admin@example.com",
    name="Administrators",
    member_of=[]
)

# Create a user
user = rbac.add_user(
    email="john@example.com",
    firstname="John",
    fullname="John Doe",
    password="secure_password",
    member_of=[admin_group['object_id']]  # Add user to admin group
)

Adding Permissions

# Grant read permission to a user on a resource
rbac.add_permission(
    identity_key=user['object_id'],
    target_oid="document_123",
    privilege="read"
)

# Grant write permission to a group (affects all members)
rbac.add_permission(
    identity_key=admin_group['object_id'],
    target_oid="document_123",
    privilege="write"
)

Checking Permissions

# Check if user has permission
has_read = rbac.has_permission(
    identity_key=user['object_id'],
    target_oid="document_123",
    privilege="read"
)

print(f"User has read permission: {has_read}")

Advanced Features

Recursive Group Memberships

Groups can contain other groups, creating a hierarchy:

# Create nested groups
root_group = rbac.add_group(email="root@example.com", name="Root", member_of=[])
middle_group = rbac.add_group(email="middle@example.com", name="Middle", member_of=[root_group['object_id']])
leaf_group = rbac.add_group(email="leaf@example.com", name="Leaf", member_of=[middle_group['object_id']])

# Add user to leaf group
user = rbac.add_user(
    email="user@example.com",
    firstname="User",
    fullname="Test User",
    password="password",
    member_of=[leaf_group['object_id']]
)

# User now has permissions granted to any of the parent groups

Time-Bound Permissions

Permissions can be granted for specific time periods:

import datetime as dt

rbac.add_permission(
    identity_key=user['object_id'],
    target_oid="document_123",
    privilege="read",
    starts=dt.datetime(2023, 1, 1),
    ends=dt.datetime(2023, 12, 31)
)

Edge Cases and Assumptions

  • Circular group memberships are prevented by the recursive view logic
  • Non-existent targets in permissions are allowed (flexible resource modeling)
  • Time-bound permissions with precise datetime validation
  • Wildcard permissions that grant broad access rights (using "*")
  • Case-insensitive email handling
  • Automatic cleanup of related records when identities are removed
  • Passwords are stored securely with HMAC-SHA512 and per-entry random salts
  • Group names can be used as lookup keys for groups
  • Email addresses needn't be unique across different identity types

Setup demo database

For your own application, you'd probably want to use your own migration tool or use ours. But you'd have a list of migrations where you will want to include these from the src/edwh_auth_rbac/migrations.py file

Prepare the migration:

cd your-demo-folder
mkdir flags
export MIGRATE_URI=sqlite://storage.sqlite
export FLAG_LOCATION=./flags

Execute the migration:

$ migrate src/edwh_auth_rbac/migrations.py 
testing migrate lock file with the current version
Using lock file:  flags/migrate-e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855.complete
Using argument src/edwh_auth_rbac/migrations.py as a reference to the migrations file.
importing migrations from src/edwh_auth_rbac/migrations.py
starting migrate hook
2 migrations discovered
table not found, starting database restore
RECOVER: attempting recovery from a backup
RECOVER_DATABASE_FROM_BACKEND started 
RECOVER: /data/database_to_restore.NOTFOUND not found. Starting from scratch.
test: rbac_tables
run:  rbac_tables
ran:  rbac_tables successfully (0.01s wall, 0.00s CPU)
test: rbac_views
run:  rbac_views
ran:  rbac_views successfully (0.00s wall, 0.00s CPU)
migration completed successfully, marking success.

Execute the example.py demo:

$ python3 example.py 
=== Creating Users and Groups and Documents ===
Created document item: {'object_id': '208247a1-cf2f-4f4e-a0c9-3edc813a78b6', 'email': 'document@example.com', 'name': 'Test Document'}
Created admin group: {'object_id': '481c6a16-672f-43b7-ad71-2b1830a3dc09', 'email': 'admin@example.com', 'name': 'Administrators'}
Created user: {'object_id': 'c797b2da-47b4-42a4-ab1d-2c0b6150555f', 'email': 'john@example.com', 'firstname': 'John', 'fullname': 'John Doe'}

=== Adding Permissions ===
Granted read permission to user on document_123
Granted write permission to admin group on document_123

=== Checking Permissions ===
User has read permission: True
User has write permission: True

=== Example completed successfully! ===

Database Schema

The library creates the following tables:

  • identity: Core identity records with object_id, type, and credentials
  • membership: Direct membership relationships between identities
  • permission: Time-bound privilege grants from identity to target
  • recursive_memberships: View showing all indirect memberships
  • recursive_members: View showing all indirect members

API Reference

For detailed API documentation, see the docstrings in the source code:

  • AuthRbac class in src/edwh_auth_rbac/rbac.py
  • Model functions in src/edwh_auth_rbac/model.py

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

edwh_auth_rbac-0.7.2.tar.gz (21.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

edwh_auth_rbac-0.7.2-py3-none-any.whl (17.3 kB view details)

Uploaded Python 3

File details

Details for the file edwh_auth_rbac-0.7.2.tar.gz.

File metadata

  • Download URL: edwh_auth_rbac-0.7.2.tar.gz
  • Upload date:
  • Size: 21.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: python-httpx/0.28.1

File hashes

Hashes for edwh_auth_rbac-0.7.2.tar.gz
Algorithm Hash digest
SHA256 f55d32fdb3ad5a41f90e7531cf06c6a312b55d621c7d75a3f7313c60e63df5fd
MD5 a76e32a9589a40afce518b033ca763fa
BLAKE2b-256 442c9efbffffaa5e38fe88427e40f95deb4c2f5c0209ac3ec4f995599ba0d06d

See more details on using hashes here.

File details

Details for the file edwh_auth_rbac-0.7.2-py3-none-any.whl.

File metadata

File hashes

Hashes for edwh_auth_rbac-0.7.2-py3-none-any.whl
Algorithm Hash digest
SHA256 a0dfdf5dc129ae7b9bb5718574649ed54bfc171c792b1a9e5224a29deec0d8f5
MD5 85b7286444591af03069c1061d4de26d
BLAKE2b-256 4f27e9cd8f11d1c1a7be7fedea254399b3ddf40a6707ea2f857fcd37c0d6ea1b

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page