Load parent environment file automatically

This commit is contained in:
2026-07-22 09:10:59 +02:00
parent 9501fdcd25
commit 9518bb8c6a
3 changed files with 93 additions and 3 deletions
+80 -2
View File
@@ -4,14 +4,92 @@ declare(strict_types=1);
/**
* Shared configuration, storage and abuse-protection helpers.
*
* Secrets are read from environment variables. The legacy env_vars.php file is
* loaded when present so existing installations keep working during migration.
* Secrets are read from process variables or from ../.env. The legacy
* env_vars.php file is loaded when present so existing installations keep
* working during migration.
*/
function app_load_env_file(string $filename): void
{
if (!is_file($filename)) {
return;
}
if (!is_readable($filename)) {
error_log('Environment file is not readable: ' . $filename);
return;
}
$size = filesize($filename);
if ($size !== false && $size > 65536) {
error_log('Environment file is unexpectedly large: ' . $filename);
return;
}
$lines = file($filename, FILE_IGNORE_NEW_LINES);
if ($lines === false) {
error_log('Environment file could not be read: ' . $filename);
return;
}
foreach ($lines as $lineNumber => $line) {
if ($lineNumber === 0) {
$line = preg_replace('/^\xEF\xBB\xBF/', '', $line) ?? $line;
}
$line = trim($line);
if ($line === '' || $line[0] === '#') {
continue;
}
if (strncmp($line, 'export ', 7) === 0) {
$line = ltrim(substr($line, 7));
}
$separator = strpos($line, '=');
if ($separator === false) {
error_log('Ignoring invalid environment entry on line ' . ($lineNumber + 1) . '.');
continue;
}
$name = trim(substr($line, 0, $separator));
if (preg_match('/^[A-Za-z_][A-Za-z0-9_]*$/', $name) !== 1) {
error_log('Ignoring invalid environment variable name on line ' . ($lineNumber + 1) . '.');
continue;
}
// Real process variables and legacy configuration always take precedence.
if (getenv($name) !== false) {
continue;
}
$value = trim(substr($line, $separator + 1));
$valueLength = strlen($value);
if ($valueLength >= 2 && $value[0] === '"' && $value[$valueLength - 1] === '"') {
$value = stripcslashes(substr($value, 1, -1));
} elseif ($valueLength >= 2 && $value[0] === "'" && $value[$valueLength - 1] === "'") {
$value = substr($value, 1, -1);
} else {
$value = preg_replace('/\s+#.*$/', '', $value) ?? $value;
$value = rtrim($value);
}
if (strpos($value, "\0") !== false) {
error_log('Ignoring environment value containing a null byte on line ' . ($lineNumber + 1) . '.');
continue;
}
putenv($name . '=' . $value);
$_ENV[$name] = $value;
}
}
$legacyEnvFile = __DIR__ . '/env_vars.php';
if (is_file($legacyEnvFile)) {
require_once $legacyEnvFile;
}
app_load_env_file(dirname(__DIR__) . DIRECTORY_SEPARATOR . '.env');
function app_env(string $name, string $default = ''): string
{
$value = getenv($name);