grazulex / laravel-configrypt
Encrypt sensitive values in your Laravel .env file and decrypt them automatically at runtime β safe, seamless, and config-driven.
Fund package maintenance!
Grazulex
paypal.me/strauven
Requires
- php: ^8.3
- illuminate/console: ^12.19
- illuminate/encryption: ^12.19
- illuminate/support: ^12.19
Requires (Dev)
- doctrine/dbal: ^4.2
- larastan/larastan: ^3.4
- laravel/pint: ^1.22
- orchestra/testbench: ^10.0
- pestphp/pest: ^3.8
- pestphp/pest-plugin-laravel: ^3.2
- rector/rector: ^2.0
Suggests
- pestphp/pest: Required to run and generate Configrypt tests (version >=3.0)
README
Encrypt sensitive values in your Laravel .env file and decrypt them automatically at runtime β safe, seamless, and config-driven.
π Overview
π Laravel Configrypt lets you encrypt secrets directly in your .env
file using a secure key, and automatically decrypts them when accessed via Laravelβs env()
or configuration helpers.
It protects values like API tokens, database credentials, or secret keys β especially when sharing .env
files across environments or storing encrypted configs in source control or CI/CD.
β¨ Features
- π Encrypt
.env
values using AES-256 - π Transparent decryption at runtime
- π§ Seamless Laravel integration via service provider
- π Custom encryption key support (fallback to
APP_KEY
) - π¦ Works with both
env()
andconfig()
helpers - π‘οΈ Secure by default: decryption only happens inside app runtime
- βοΈ Configurable via
config/configrypt.php
- π§ͺ Safe for CI/CD, secrets rotation, and external vault injection
π‘ Example
In your .env
:
MAIL_PASSWORD=ENC:gk9AvRZgx6Jyds7K2uFctw==
In your Laravel code:
// Method 1: Use helper functions (recommended) $password = configrypt_env('MAIL_PASSWORD'); // returns decrypted value $password = encrypted_env('MAIL_PASSWORD'); // alias for configrypt_env() // Method 2: Use the Str macro for easy migration use Illuminate\Support\Str; $password = Str::decryptEnv('MAIL_PASSWORD'); // easy search & replace from env() // Method 3: Use the environment facade use LaravelConfigrypt\Facades\ConfigryptEnv; $password = ConfigryptEnv::get('MAIL_PASSWORD'); // returns decrypted value // Method 4: Manual decryption use LaravelConfigrypt\Facades\Configrypt; $rawValue = env('MAIL_PASSWORD'); // still encrypted due to Laravel's env cache $password = Configrypt::decrypt($rawValue); // manual decrypt // Note: env('MAIL_PASSWORD') returns encrypted value due to Laravel's cache limitation
βοΈ Configuration
Publish the config:
php artisan vendor:publish --tag=configrypt-config
Result in config/configrypt.php
:
return [ // Use a dedicated key or fallback to APP_KEY 'key' => env('CONFIGRYPT_KEY', env('APP_KEY')), // Prefix used to identify encrypted values 'prefix' => env('CONFIGRYPT_PREFIX', 'ENC:'), // Cipher method 'cipher' => env('CONFIGRYPT_CIPHER', 'AES-256-CBC'), // Automatically decrypt during early bootstrap (default: false) // When true, encrypted env vars are decrypted during service provider registration 'auto_decrypt' => env('CONFIGRYPT_AUTO_DECRYPT', false), ];
π Quick Start
1. Install the package
composer require grazulex/laravel-configrypt
2. Publish configuration (optional)
php artisan vendor:publish --tag=configrypt-config
3. Encrypt your secrets
php artisan configrypt:encrypt "my-super-secret-password"
Output:
Encrypted value:
ENC:gk9AvRZgx6Jyds7K2uFctw==
You can now use this encrypted value in your .env file:
SOME_SECRET=ENC:gk9AvRZgx6Jyds7K2uFctw==
4. Add to your .env file
DB_PASSWORD=ENC:gk9AvRZgx6Jyds7K2uFctw== API_SECRET=ENC:XyZ123AbC456DeF789GhI012JkL== JWT_SECRET=ENC:MnOpQrStUvWxYzAbCdEfGhIjKl==
5. Use in your application
β οΈ Important: Laravel's env()
function cannot be automatically decrypted due to early caching.
// β This won't work - Laravel caches env() before our package loads $dbPassword = env('DB_PASSWORD'); // Returns "ENC:xyz..." (still encrypted) // β Use our helper functions instead (recommended) $dbPassword = configrypt_env('DB_PASSWORD'); // Returns decrypted value $apiSecret = encrypted_env('API_SECRET'); // Alias for consistency // β Or use the facade for more control use LaravelConfigrypt\Facades\ConfigryptEnv; $dbPassword = ConfigryptEnv::get('DB_PASSWORD'); // β Or use the Str macro for easy migration use Illuminate\Support\Str; $dbPassword = Str::decryptEnv('DB_PASSWORD'); // β Enable auto-decryption to bypass Laravel's env cache (advanced) // Set CONFIGRYPT_AUTO_DECRYPT=true in .env to decrypt during early bootstrap
β οΈ Important: Laravel env() Cache Limitation
Laravel caches environment variables very early in the boot process, before service providers load. This means the standard env()
function cannot be automatically decrypted.
π§ Migration Solutions
Option 1: Use Helper Functions (Recommended)
// β This won't work - returns encrypted value $password = env('DB_PASSWORD'); // Still returns "ENC:xyz..." // β These work - return decrypted values $password = configrypt_env('DB_PASSWORD'); $password = encrypted_env('DB_PASSWORD'); $password = ConfigryptEnv::get('DB_PASSWORD');
Option 2: Use Str Macro (Easy Migration)
use Illuminate\Support\Str; // Easy to search and replace in your codebase $password = Str::decryptEnv('DB_PASSWORD');
Option 3: Enable Auto-Decryption (Advanced)
// Set in .env file: CONFIGRYPT_AUTO_DECRYPT=true // This enables early decryption that bypasses Laravel's env cache // After enabling, env() will return decrypted values $password = env('DB_PASSWORD'); // Now returns decrypted value
Option 4: Manual Decryption
use LaravelConfigrypt\Facades\Configrypt; $rawValue = env('DB_PASSWORD'); $password = Configrypt::isEncrypted($rawValue) ? Configrypt::decrypt($rawValue) : $rawValue;
π Quick Migration
Option A: Enable Auto-Decryption (Recommended)
# Add to your .env file echo "CONFIGRYPT_AUTO_DECRYPT=true" >> .env # Now env() calls work normally - no code changes needed! # Your existing env() calls will return decrypted values
Option B: Find and Replace in Codebase
# Replace env() calls with configrypt_env() find . -name "*.php" -exec sed -i 's/env(/configrypt_env(/g' {} \; # Or use Str::decryptEnv() for easier reversal find . -name "*.php" -exec sed -i 's/env(/Str::decryptEnv(/g' {} \;
π§ Advanced Usage
Using the Facades
use LaravelConfigrypt\Facades\Configrypt; use LaravelConfigrypt\Facades\ConfigryptEnv; // Encrypt a value $encrypted = Configrypt::encrypt('my-secret-value'); // Decrypt a value $decrypted = Configrypt::decrypt('ENC:encrypted-value'); // Check if a value is encrypted $isEncrypted = Configrypt::isEncrypted('ENC:some-value'); // Environment-specific methods $dbPassword = ConfigryptEnv::get('DB_PASSWORD'); $allDecrypted = ConfigryptEnv::getAllDecrypted(); ConfigryptEnv::decryptAll(); // Process all ENC: prefixed variables
Helper Functions
// Primary helper functions (recommended approach) $dbPassword = configrypt_env('DB_PASSWORD', 'default-value'); $apiKey = encrypted_env('API_KEY'); // alias for configrypt_env() // Str macro for easy migration from env() calls use Illuminate\Support\Str; $secret = Str::decryptEnv('JWT_SECRET');
Auto-Decryption Feature
// Enable in .env file: CONFIGRYPT_AUTO_DECRYPT=true // This enables early decryption during service provider registration // After enabling, Laravel's env() function returns decrypted values: $password = env('DB_PASSWORD'); // Returns decrypted value // The auto-decryption feature: // 1. Decrypts all ENC: prefixed env vars during early bootstrap // 2. Updates $_ENV, $_SERVER, and putenv() // 3. Clears Laravel's environment cache to ensure env() returns decrypted values // 4. Handles errors gracefully (silent in production, logged in debug mode)
Dependency Injection
use LaravelConfigrypt\Services\ConfigryptService; use LaravelConfigrypt\Services\EnvironmentDecryptor; class MyController extends Controller { public function __construct( private ConfigryptService $configrypt, private EnvironmentDecryptor $envDecryptor ) { } public function encryptValue(Request $request) { $encrypted = $this->configrypt->encrypt($request->value); return response()->json(['encrypted' => $encrypted]); } public function getDecryptedEnv(string $key) { return $this->envDecryptor->get($key); } }
π§ͺ Practical Examples
Database Configuration
# Encrypt your database password DB_PASSWORD=ENC:W3+f/2ZzZfl9KQ==
// config/database.php 'mysql' => [ 'driver' => 'mysql', 'password' => configrypt_env('DB_PASSWORD'), // Use helper function // OR if auto-decryption is enabled: 'password' => env('DB_PASSWORD'), // Works with auto-decrypt enabled ],
API Keys Management
# Third-party service credentials STRIPE_SECRET=ENC:Nq8j8hlc3PMp9uE= MAILGUN_SECRET=ENC:XYZ123456789abc= AWS_SECRET_ACCESS_KEY=ENC:AbCdEf1234567890=
// config/services.php 'stripe' => [ 'secret' => configrypt_env('STRIPE_SECRET'), // OR with auto-decrypt: 'secret' => env('STRIPE_SECRET'), ], 'mailgun' => [ 'secret' => configrypt_env('MAILGUN_SECRET'), // OR with auto-decrypt: 'secret' => env('MAILGUN_SECRET'), ], // config/filesystems.php 's3' => [ 'driver' => 's3', 'secret' => configrypt_env('AWS_SECRET_ACCESS_KEY'), // OR with auto-decrypt: 'secret' => env('AWS_SECRET_ACCESS_KEY'), ],
Multi-Environment Setup
# Development CONFIGRYPT_KEY=dev-key-32-characters-long----- CONFIGRYPT_AUTO_DECRYPT=true DB_PASSWORD=ENC:dev-encrypted-password # Production CONFIGRYPT_KEY=prod-key-32-characters-long---- CONFIGRYPT_AUTO_DECRYPT=true DB_PASSWORD=ENC:prod-encrypted-password
More examples available in the examples/
directory.
π Changing Keys
You can define a custom CONFIGRYPT_KEY
in .env
to use a dedicated encryption key different from APP_KEY
.
π‘ Remember: only encrypted values with the correct key can be decrypted. Keep your key safe!
π‘οΈ Security Considerations
- Auto-Decryption Security: When
CONFIGRYPT_AUTO_DECRYPT=true
, decryption happens during early bootstrap and values are stored in memory only - Environment Variable Safety: Decrypted values never touch disk after load, only stored in runtime memory
- Prefix Protection:
ENC:
prefix ensures only intended values are decrypted - Error Handling: Graceful fallbacks prevent application crashes from decryption failures
- Key Management: Only encrypted values with the correct key can be decrypted - keep your key safe!
- Production Usage: Ideal for
.env.staging
,.env.production
, or vault-managed.env
overrides - Team Sharing: Perfect for sharing
.env
securely in teams or across pipelines
π Quick Start
# 1. Install the package composer require grazulex/laravel-configrypt # 2. Publish configuration (optional) php artisan vendor:publish --tag=configrypt-config # 3. Enable auto-decryption (recommended) echo "CONFIGRYPT_AUTO_DECRYPT=true" >> .env # 4. Encrypt a secret php artisan configrypt:encrypt "your-secret-value" # 5. Add to .env file echo "MY_SECRET=ENC:your-encrypted-value" >> .env # 6. Use in your application (multiple options) # Option A: Works automatically with auto-decrypt enabled $secret = env('MY_SECRET'); # Option B: Use helper functions (always works) $secret = configrypt_env('MY_SECRET'); # Option C: Use Str macro for easy migration $secret = Str::decryptEnv('MY_SECRET');
π Documentation
Comprehensive documentation is available in the docs/
directory:
- Installation - Getting started with Laravel Configrypt
- Configuration - Customizing encryption settings
- Basic Usage - Fundamental encryption/decryption operations
- Advanced Usage - Complex scenarios and integrations
- Artisan Commands - Command-line tools reference
- API Reference - Complete API documentation
- Security Considerations - Security best practices
- Troubleshooting - Common issues and solutions
- Examples - Practical usage examples
π License
MIT License β see LICENSE.md
Made with π for Laravel developers who care about secrets.