v2

Configuration Guide

Purpose: Comprehensive reference for all configuration options, environment variables, and feature flags
Target: Development, Staging, Production


📋 Environment Variables

Application

# Core
APP_NAME=Loreax
APP_ENV=local|test|hyena|prod      # Environment: local, test, hyena (staging), prod
APP_KEY=base64:xxxx...              # Generated via: php artisan key:generate
APP_DEBUG=true|false                # Debug mode (false in production)
APP_URL=http://localhost:8000       # Application URL (public)
APP_FRONTEND_URL=http://localhost   # Frontend SPA URL (for CORS, redirects)

# Timezone
APP_TIMEZONE=Africa/Nairobi          # Timezone for all timestamps

Database — PostgreSQL

DB_CONNECTION=pgsql
DB_HOST=127.0.0.1
DB_PORT=5432
DB_DATABASE=loreax
DB_USERNAME=loreax
DB_PASSWORD=secret
DB_URL=                              # Optional: full connection string overrides individual vars

Cache — Redis

CACHE_DRIVER=redis                   # Driver: redis, file, array
REDIS_HOST=127.0.0.1
REDIS_PORT=6379
REDIS_PASSWORD=null
REDIS_DB=0

Session

SESSION_DRIVER=cookie|redis          # Driver: cookie (stateless), redis (stateful)
SESSION_LIFETIME=120                 # Minutes
SESSION_DOMAIN=null
SESSION_PATH=/
SESSION_SECURE=false                 # true in production (HTTPS only)
SESSION_HTTP_ONLY=true               # Prevent JavaScript access
SESSION_SAME_SITE=lax|strict         # CSRF protection

Queue & Jobs

QUEUE_CONNECTION=redis               # Driver: sync, redis, database
QUEUE_FAILED_DRIVER=database         # Failed job storage
HORIZON_PREFIX=horizon               # Redis prefix for Horizon

Logging

LOG_CHANNEL=stack                    # Channel: single, stack, daily
LOG_STACK=single                     # Stack channels (comma-separated)
LOG_LEVEL=debug|info|notice|warning|error|critical|alert|emergency
LOG_DAILY_DAYS=14                    # Rotate logs older than N days
LOG_DEPRECATIONS_CHANNEL=null

Mail

MAIL_MAILER=smtp|mailgun             # Mailer: smtp, mailgun, ses, mailpit
MAIL_HOST=smtp.mailtrap.io
MAIL_PORT=2525
MAIL_USERNAME=xxx
MAIL_PASSWORD=xxx
MAIL_ENCRYPTION=tls                  # null, tls, ssl
MAIL_FROM_ADDRESS=noreply@loreax.app
MAIL_FROM_NAME="Loreax"

Authentication

SANCTUM_STATEFUL_DOMAINS=localhost:3000,localhost:8000
SANCTUM_GUARD=web|api                # Guard for API tokens

MongoDB (Request Logs)

MONGODB_DSN=mongodb://user:password@host:27017/database?auth=admin
MONGODB_DATABASE=loreax_logs         # Database name for request logs
MONGODB_DSN_TEST=mongodb://localhost:27017

AWS S3 (Media Storage)

AWS_ACCESS_KEY_ID=testing
AWS_SECRET_ACCESS_KEY=testing
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=loreax-local
AWS_URL=                             # Optional: public URL for resources
AWS_ENDPOINT=                        # Optional: for S3-compatible services (MinIO)
AWS_USE_PATH_STYLE_ENDPOINT=false    # true for MinIO

Media Processing

MEDIA_DISK=s3|local                  # Storage disk for media
FFMPEG_BINARIES=/usr/bin/ffmpeg      # FFmpeg location
FFPROBE_BINARIES=/usr/bin/ffprobe    # FFprobe location

MPESA (Payments)

# Safaricom Daraja
MPESA_CONSUMER_KEY=xxx
MPESA_CONSUMER_SECRET=xxx
MPESA_PASSKEY=xxx
MPESA_BUSINESS_SHORTCODE=123456      # Till number for B2C
MPESA_CALLBACK_HOST=https://api.loreax.app

# Modes
MPESA_SANDBOX=true|false             # true for testing, false for production

Feature Flags & Platform Settings

# Feature Flags (see Platform Settings in database)
FEATURES_ENABLED=timeline,discovery,payments
FEATURES_DISABLED=notifications,promotions

# Platform Settings Overrides (use database by default)
PLATFORM_SETTINGS_CACHE_TTL=3600     # Cache duration (seconds)

Rate Limiting

RATE_LIMIT_AUTH=5,1                  # 5 attempts per 1 minute
RATE_LIMIT_PAYMENT=3,1               # 3 attempts per 1 minute
RATE_LIMIT_WRITE=30,1                # 30 requests per 1 minute
RATE_LIMIT_READ=60,1                 # 60 requests per 1 minute

MFA & Security

BCRYPT_ROUNDS=12                     # Password hashing rounds (4 in test, 12+ in prod)
GOOGLE2FA_ENABLED=true               # Enable TOTP MFA
JWT_EXPIRATION=1440                  # JWT token lifetime (minutes)

Admin Filament

FILAMENT_AUTHENTICATION_GUARD=admin  # Guard for admin users

🔧 Configuration Files

All configuration files are in config/ directory. Key files:

config/app.php

return [
    'name' => env('APP_NAME', 'Loreax'),
    'env' => env('APP_ENV', 'production'),
    'debug' => env('APP_DEBUG', false),
    'url' => env('APP_URL', 'http://localhost'),
    'timezone' => env('APP_TIMEZONE', 'UTC'),
    
    'providers' => [
        // Service providers registered here
    ],
    
    'aliases' => [
        // Facades registered here
    ],
];

config/database.php

return [
    'default' => env('DB_CONNECTION', 'pgsql'),
    
    'connections' => [
        'pgsql' => [
            'driver' => 'pgsql',
            'host' => env('DB_HOST', 'localhost'),
            'port' => env('DB_PORT', 5432),
            'database' => env('DB_DATABASE', 'loreax'),
            'username' => env('DB_USERNAME', 'loreax'),
            'password' => env('DB_PASSWORD', 'secret'),
            // ... SSL, charset options
        ],
    ],
];

config/cache.php

return [
    'default' => env('CACHE_DRIVER', 'redis'),
    
    'stores' => [
        'redis' => [
            'driver' => 'redis',
            'connection' => 'cache',
            'prefix' => env('CACHE_PREFIX', ''),
        ],
    ],
];

config/queue.php

return [
    'default' => env('QUEUE_CONNECTION', 'redis'),
    
    'connections' => [
        'redis' => [
            'driver' => 'redis',
            'connection' => 'default',
            'queue' => env('QUEUE_NAME', 'default'),
            'retry_after' => 90,
            'block_for' => null,
        ],
    ],
];

config/logging.php

return [
    'default' => env('LOG_CHANNEL', 'stack'),
    
    'channels' => [
        'stack' => [
            'driver' => 'stack',
            'channels' => ['single', 'stderr'],
            'ignore_exceptions' => false,
        ],
        
        'single' => [
            'driver' => 'single',
            'path' => storage_path('logs/laravel.log'),
            'level' => env('LOG_LEVEL', 'debug'),
        ],
        
        'daily' => [
            'driver' => 'daily',
            'path' => storage_path('logs/laravel.log'),
            'level' => env('LOG_LEVEL', 'debug'),
            'days' => env('LOG_DAILY_DAYS', 14),
        ],
    ],
];

config/filesystems.php

return [
    'default' => env('FILESYSTEM_DRIVER', 's3'),
    
    'disks' => [
        's3' => [
            'driver' => 's3',
            'key' => env('AWS_ACCESS_KEY_ID'),
            'secret' => env('AWS_SECRET_ACCESS_KEY'),
            'region' => env('AWS_DEFAULT_REGION'),
            'bucket' => env('AWS_BUCKET'),
            'url' => env('AWS_URL'),
            'endpoint' => env('AWS_ENDPOINT'),
        ],
        
        'local' => [
            'driver' => 'local',
            'root' => storage_path('app'),
        ],
    ],
];

config/permission.php

return [
    'models' => [
        'permission' => \Spatie\Permission\Models\Permission::class,
        'role' => \Spatie\Permission\Models\Role::class,
    ],
    
    'table_names' => [
        'roles' => 'roles',
        'permissions' => 'permissions',
        'model_has_permissions' => 'model_has_permissions',
        'model_has_roles' => 'model_has_roles',
        'role_has_permissions' => 'role_has_permissions',
    ],
    
    'column_names' => [
        'model_morph_key' => 'model_type',
        'team_foreign_key' => 'team_id',
    ],
    
    'cache_expiration_time' => 86400, // 24 hours
];

🚀 Environment-Specific Configurations

Local Development

APP_ENV=local
APP_DEBUG=true
LOG_LEVEL=debug

# Single request/response cycle (no persistence)
CACHE_DRIVER=array
SESSION_DRIVER=cookie

# Use local S3 mock (MinIO)
AWS_ENDPOINT=http://127.0.0.1:9000
AWS_USE_PATH_STYLE_ENDPOINT=true

# Test credentials
MPESA_SANDBOX=true

Testing

APP_ENV=test
APP_DEBUG=true
LOG_LEVEL=debug

# In-memory database
DB_DATABASE=:memory:

# File-based cache
CACHE_DRIVER=file

# Sync queue (no background processing)
QUEUE_CONNECTION=sync

# Test database/credentials
MPESA_SANDBOX=true

Staging (Hyena)

APP_ENV=hyena
APP_DEBUG=false
LOG_LEVEL=info

# Production-like setup
CACHE_DRIVER=redis
QUEUE_CONNECTION=redis
SESSION_DRIVER=redis

# HTTPS required
SESSION_SECURE=true
SESSION_SAME_SITE=strict

# Real MPESA (sandbox)
MPESA_SANDBOX=true

# Real AWS S3
AWS_BUCKET=loreax-staging

Production

APP_ENV=prod
APP_DEBUG=false
LOG_LEVEL=warning

# Full caching
CACHE_DRIVER=redis
QUEUE_CONNECTION=redis
SESSION_DRIVER=redis

# Security hardened
SESSION_SECURE=true
SESSION_SAME_SITE=strict
BCRYPT_ROUNDS=12

# Real MPESA (production)
MPESA_SANDBOX=false

# Real AWS S3
AWS_BUCKET=loreax-production

🎛️ Platform Settings (Database)

Dynamic settings stored in platform_settings table:

Key Type Default Description
post_purchase_fee_percentage int 15 Platform fee on purchases (%)
creator_earnings_hold_hours int 72 Hours before creator can withdraw earnings
withdrawal_minimum_amount int 10000 Minimum withdrawal (smallest unit, e.g., 100 KES)
withdrawal_maximum_amount int 1000000 Maximum withdrawal per request
subscription_tier_min_price int 100 Minimum tier price (smallest unit)
subscription_tier_max_price int 50000 Maximum tier price
welcome_bonus_amount int 0 New user cash bonus
referral_commission_percentage float 10 Referral bonus (%)
content_processing_enabled bool true Enable media processing
ai_prescreen_moderation string 'off' off, review, auto_action
email_notifications_enabled bool true Enable email notifications

Access in code:

// Get setting
$fee = app(IPlatformSettings::class)->get('post_purchase_fee_percentage');

// Use in controller
public function purchase(Request $request, IPlatformSettings $settings)
{
    $fee = $settings->get('post_purchase_fee_percentage');
    // ...
}

🚦 Feature Flags

Located in feature_flags table. Enable/disable features without deployment:

Flag Type Description
timeline_v2 bool New timeline algorithm
ai_moderation bool Enable AI content screening
mpesa_c2b_topup bool Enable customer-to-business top-ups
livestream_enabled bool Allow creators to go live
fan_club_enabled bool Allow creator community spaces

Check in code:

if (app(IFeatureFlags::class)->isEnabled('ai_moderation')) {
    // Run AI screening
}

📝 Configuration Checklist

Before deploying to production:

  • APP_DEBUG=false (never true in production)
  • APP_ENV=prod
  • BCRYPT_ROUNDS=12 (minimum)
  • SESSION_SECURE=true (HTTPS only)
  • SESSION_SAME_SITE=strict
  • LOG_LEVEL=warning (not debug/info)
  • All database credentials set correctly
  • Redis connection verified
  • MongoDB connection verified
  • AWS S3 credentials correct for production bucket
  • MPESA credentials are production (not sandbox)
  • Email service configured
  • SMS service configured (if used)
  • All secrets rotated (not defaults from .env.example)
  • SSL certificates installed on server
  • Rate limits appropriate for expected traffic
  • Backup strategy in place

📞 Support

  • Questions: Check relevant domain README in docs/wikis/<domain>/
  • Issues: GitHub Issues
  • Slack: #loreax-dev

Last Updated: April 25, 2026