Skip to main content

Django-inspired modular framework for Discord bots

Project description

HazelAura

Django-inspired modular framework for Discord bots.

pip install hazelaura
aura create --project mybot
cd mybot && aura run dev

Feature Overview

Feature Description
Settings system core/settings.py — Django-style central config with env-var overrides
Auto-discovery INSTALLED_APPS — zero-import app loading (commands, events, services)
Middleware pipeline Async middleware chain runs before every command
Dependency injection Named services auto-injected into command parameters
Command router Decorator-based router.command() — register anywhere, flush at startup
Superuser system aura createsuperuser + @is_superuser() decorator
Role-based auth @require_roles() / @require_permissions() decorators
Global error handler Clean, structured error responses for all failure modes
Hot-reload aura run dev watches for file changes and reloads extensions
Interactive shell aura shell — IPython/code.interact with full project context
Built-in DB SQLite via DatabaseService (swap engine in settings)
Built-in cache In-memory TTL cache via CacheService

Project Structure

mybot/
├── core/
│   └── settings.py          ← All configuration
├── cogs/
│   └── example/
│       ├── __init__.py
│       ├── commands.py      ← Cog + commands (auto-discovered)
│       ├── events.py        ← Event listeners (auto-discovered)
│       ├── services.py      ← Business logic layer
│       └── models.py        ← Data-access helpers
├── utils/
├── data/                    ← SQLite DB + logs (git-ignored)
├── .env                     ← Secrets (git-ignored)
├── main.py
└── requirements.txt

CLI Reference

aura create --project <n>    Scaffold a new project
aura create --app <n>        Scaffold a new cog/app
aura run dev                    Start bot with hot-reload
aura migrate                    Run DB schema migrations
aura createsuperuser            Register a Discord superuser
aura shell                      Interactive Python shell
aura help                       Show help

Settings

# core/settings.py
from hazelaura.core.settings import BaseSettings

class Settings(BaseSettings):
    TOKEN           = os.getenv("DISCORD_TOKEN")
    PREFIX          = "!"
    DEBUG           = True
    INSTALLED_APPS  = ["cogs.music", "cogs.admin"]
    MIDDLEWARE      = [
        "hazelaura.core.builtin.middleware.logging_middleware",
        "mybot.core.middleware.my_custom_middleware",
    ]
    DATABASE = {"ENGINE": "sqlite", "NAME": "data/db.sqlite3"}

settings = Settings()

Every attribute can be overridden by an environment variable prefixed HAZEL_, e.g. HAZEL_PREFIX=>> overrides PREFIX.


Auto-Discovery

List your app packages in INSTALLED_APPS. HazelAura will automatically import commands.py, events.py, and services.py from each package and register any discord.ext.commands.Cog subclasses with the bot.

INSTALLED_APPS = [
    "cogs.music",
    "cogs.moderation",
    "cogs.economy",
]

Each app follows the convention:

cogs/music/
├── __init__.py
├── commands.py    ← defines MusicCommands(commands.Cog)  + setup()
├── events.py      ← defines MusicEvents(commands.Cog)    + setup()
└── services.py    ← MusicService class

Middleware

# core/settings.py
MIDDLEWARE = [
    "hazelaura.core.builtin.middleware.logging_middleware",
    "mybot.core.middleware.rate_limit_middleware",
]

# mybot/core/middleware.py
async def rate_limit_middleware(ctx, call_next):
    if is_rate_limited(ctx.author.id):
        return await ctx.send("⏳ Slow down!")
    await call_next(ctx)

Dependency Injection

from hazelaura.core.injector import injector

# Register a custom service
injector.register("payments", PaymentService())

# Auto-inject into commands by parameter name
@bot.command()
async def subscribe(ctx, db, cache, payments):
    user = db.fetchone("SELECT * FROM users WHERE id=?", (ctx.author.id,))
    ...

Auth Decorators

from hazelaura import is_superuser, require_roles, require_permissions

@bot.command()
@is_superuser()
async def shutdown(ctx): ...

@bot.command()
@require_roles("Admin", "Moderator")
async def ban(ctx, member): ...

@bot.command()
@require_permissions(manage_guild=True)
async def settings_cmd(ctx): ...

Command Router

Register commands anywhere — in any module — without touching the bot object:

from hazelaura.core.router import router

@router.command("ping")
async def ping(ctx):
    await ctx.send("pong")

@router.group("admin")
async def admin(ctx):
    pass

@router.subcommand("admin", "reload")
async def admin_reload(ctx, extension: str):
    await ctx.bot.reload_extension(extension)
    await ctx.send(f"✅ Reloaded {extension}")

Superuser System

# Register a superuser
aura createsuperuser
# → Enter the Discord user ID

# Or non-interactively
aura createsuperuser --id 123456789012345678
from hazelaura import is_superuser

@bot.command()
@is_superuser()
async def secret(ctx):
    await ctx.send("🔐 Superuser-only command!")

License

MIT — HazelTech 🦕

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

hazelaura-1.0.4.tar.gz (28.8 kB view details)

Uploaded Source

Built Distribution

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

hazelaura-1.0.4-py3-none-any.whl (34.6 kB view details)

Uploaded Python 3

File details

Details for the file hazelaura-1.0.4.tar.gz.

File metadata

  • Download URL: hazelaura-1.0.4.tar.gz
  • Upload date:
  • Size: 28.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.6

File hashes

Hashes for hazelaura-1.0.4.tar.gz
Algorithm Hash digest
SHA256 b898a2ae5a71bbba18a0751308b67def32d7036f3c24ae4047e3f56b9be9ba09
MD5 f4cc03b2244582a5fee0dc888f595557
BLAKE2b-256 91600500e97fa9d6e8b3b91739969b84bea82631648d7333328902f69a6c201c

See more details on using hashes here.

File details

Details for the file hazelaura-1.0.4-py3-none-any.whl.

File metadata

  • Download URL: hazelaura-1.0.4-py3-none-any.whl
  • Upload date:
  • Size: 34.6 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.6

File hashes

Hashes for hazelaura-1.0.4-py3-none-any.whl
Algorithm Hash digest
SHA256 2092717412129681e1e4a03a0696880b1b90afc7e98190cf96d8213641744af3
MD5 f026ed51c4f5e8db066a5b34762d1429
BLAKE2b-256 f14b7d623455ce8054d312bef9a0e715959bb9e07c7bf77ce05ecf515f34cfb9

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